
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
  "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">


<html xmlns="http://www.w3.org/1999/xhtml">
  <head>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
    
    <title>odespy.solvers &mdash; Odespy API 0.2 documentation</title>
    
    <link rel="stylesheet" href="../../_static/pyramid.css" type="text/css" />
    <link rel="stylesheet" href="../../_static/pygments.css" type="text/css" />
    
    <script type="text/javascript">
      var DOCUMENTATION_OPTIONS = {
        URL_ROOT:    '../../',
        VERSION:     '0.2',
        COLLAPSE_INDEX: false,
        FILE_SUFFIX: '.html',
        HAS_SOURCE:  true
      };
    </script>
    <script type="text/javascript" src="../../_static/jquery.js"></script>
    <script type="text/javascript" src="../../_static/underscore.js"></script>
    <script type="text/javascript" src="../../_static/doctools.js"></script>
    <script type="text/javascript" src="http://cdn.mathjax.org/mathjax/latest/MathJax.js?config=TeX-AMS-MML_HTMLorMML"></script>
    <link rel="top" title="Odespy API 0.2 documentation" href="../../index.html" />
    <link rel="up" title="Module code" href="../index.html" />
<link rel="stylesheet" href="http://fonts.googleapis.com/css?family=Neuton&amp;subset=latin" type="text/css" media="screen" charset="utf-8" />
<link rel="stylesheet" href="http://fonts.googleapis.com/css?family=Nobile:regular,italic,bold,bolditalic&amp;subset=latin" type="text/css" media="screen" charset="utf-8" />
<!--[if lte IE 6]>
<link rel="stylesheet" href="../../_static/ie6.css" type="text/css" media="screen" charset="utf-8" />
<![endif]-->

  </head>
  <body>

    <div class="related">
      <h3>Navigation</h3>
      <ul>
        <li class="right" style="margin-right: 10px">
          <a href="../../genindex.html" title="General Index"
             accesskey="I">index</a></li>
        <li class="right" >
          <a href="../../py-modindex.html" title="Python Module Index"
             >modules</a> |</li>
        <li class="right" >
          <a href="../../np-modindex.html" title="Python Module Index"
             >modules</a> |</li>
        <li><a href="../../index.html">Odespy API 0.2 documentation</a> &raquo;</li>
          <li><a href="../index.html" accesskey="U">Module code</a> &raquo;</li> 
      </ul>
    </div>  

    <div class="document">
      <div class="documentwrapper">
        <div class="bodywrapper">
          <div class="body">
            
  <h1>Source code for odespy.solvers</h1><div class="highlight"><pre>
<span class="c"># Author: Liwei Wang, Hans Petter Langtangen</span>

<span class="sd">&#39;&#39;&#39;</span>
<span class="sd">This module contains the base class ``Solver``</span>
<span class="sd">package and the implementations of many subclasses.</span>

<span class="sd">A new non-adaptive time-stepping scheme can often be implemented by</span>
<span class="sd">just subclassing ``Solver`` and writing the ``advance`` method</span>
<span class="sd">to define the time-stepping scheme. Here is how the 4th-order</span>
<span class="sd">Runge-Kutta is implemented::</span>

<span class="sd">    class RK4(Solver):</span>
<span class="sd">        quick_description = &quot;Explicit 4th-order Runge-Kutta method&quot;</span>

<span class="sd">        def advance(self):</span>
<span class="sd">            u, f, n, t = self.u, self.f, self.n, self.t</span>
<span class="sd">            dt = t[n+1] - t[n]</span>
<span class="sd">            dt2 = dt/2.0</span>
<span class="sd">            K1 = dt*f(u[n], t[n])</span>
<span class="sd">            K2 = dt*f(u[n] + 0.5*K1, t[n] + dt2)</span>
<span class="sd">            K3 = dt*f(u[n] + 0.5*K2, t[n] + dt2)</span>
<span class="sd">            K4 = dt*f(u[n] + K3, t[n] + dt)</span>
<span class="sd">            u_new = u[n] + (1/6.0)*(K1 + 2*K2 + 2*K3 + K4)</span>
<span class="sd">            return u_new</span>

<span class="sd">The ``quick_description`` string is needed for the class to appear</span>
<span class="sd">in the package&#39;s table of contents.</span>

<span class="sd">Implicit solver: See examples in the ``solver.py`` file,</span>
<span class="sd">class ``BackwardEuler``, for instance.</span>

<span class="sd">Adaptive solver: See examples in the ``solver.py`` file, class ``RKFehlberg``,</span>
<span class="sd">for instance.</span>

<span class="sd">*Wrapping other packages*.</span>
<span class="sd">This section is for developers who intend to wrap an existing</span>
<span class="sd">package and integrate with the present one..</span>

<span class="sd">If the original package is not written in Python language, developers</span>
<span class="sd">need to apply some specific tools (like F2PY, Cython, or SWIG) to create an</span>
<span class="sd">extension module to make the package accessible from Python</span>
<span class="sd">code.</span>

<span class="sd">On the other hand, if the original package is also a Python software,</span>
<span class="sd">developers need to install and import (in ``initialize``) the desired</span>
<span class="sd">package as a Python module and just write a class in the ``Solver``</span>
<span class="sd">hierarchy that calls the proper functions in the package. See the</span>
<span class="sd">classes ``odefun_sympy`` and ``ode_scipy`` (and its subclasses).</span>

<span class="sd">By an attempt to import these necessary modules (often set in method</span>
<span class="sd">initialize()), we can check whether the necessary dependencies are</span>
<span class="sd">installed properly.</span>

<span class="sd">*Definition of parameters and their properties*.</span>
<span class="sd">Each solver has a set of specific parameters depending on its</span>
<span class="sd">underlying method. For example, adaptive solvers will be more</span>
<span class="sd">likely to apply (many) attributes for step-size control.</span>
<span class="sd">When integrating a new method, first search in the ``_parameters``</span>
<span class="sd">dictionary in ``solver.py`` if some parameters can be reused</span>
<span class="sd">for the new solver. New parameters are added to the ``_parameters``</span>
<span class="sd">dictionary, either in the ``solver.py`` or by importing ``solver``</span>
<span class="sd">and updating ``solver._parameters``, see ``rkc.py`` for an example.</span>

<span class="sd">Each solver class lists the required and optional parameters</span>
<span class="sd">it needs in the class variables ``_optional_parameters`` and</span>
<span class="sd">``_required_parameters``. Very often these lists are inherited,</span>
<span class="sd">or just a few new parameters are added to the list already</span>
<span class="sd">defined in the superclass.</span>

<span class="sd">Sometimes values of parameters (or other properties) need to be</span>
<span class="sd">changed in a solver, e.g., because there are certain relations between</span>
<span class="sd">various parameters. Appropriate adjustments and checks are done in the</span>
<span class="sd">method ``initialize_for_solve``, which is called in the beginning of</span>
<span class="sd">the &quot;solve&quot; process (before any computations take place).  Many</span>
<span class="sd">classes provide examples on this, e.g., class ``RKC`` in ``rkc.py``.</span>
<span class="sd">This particular class shows how to generate input parameters</span>
<span class="sd">to the Fortran code that are not given by the user, but automatically</span>
<span class="sd">derived in the Python code from other data.</span>

<span class="sd">Another method that is called from ``solve`` is ``validate_data``. The</span>
<span class="sd">solver class can use this method to check for consistency of data</span>
<span class="sd">structures before starting the numerical computations.  As an example,</span>
<span class="sd">the class ``Lsodes`` in the ``odepack.py`` file imposes relations</span>
<span class="sd">between the input data: two input integer arrays ``ia`` and ``ja``</span>
<span class="sd">must be input simultaneously, ``len(ia) == neq + 1``, and ``ia[neq] =</span>
<span class="sd">len(ja)``. These checks are done in Python before calling the Fortran</span>
<span class="sd">solver.</span>


<span class="sd">*The solve and advance methods*.</span>
<span class="sd">Simple methods can just implement ``advance`` to bring the solution</span>
<span class="sd">one step forward in time. The existing ``solve`` method derived from</span>
<span class="sd">the superclass is general enough to administer the whole solution</span>
<span class="sd">process.</span>

<span class="sd">Adaptive solvers will typically think of ``advance`` as bringing the</span>
<span class="sd">solution to the next user-desired time level, using an unknown set of</span>
<span class="sd">smaller time steps whose sizes must be determined. Then there will</span>
<span class="sd">hence be a time loop within ``advance``, while the outer time loop in</span>
<span class="sd">``solve`` takes care of the stepping between the user-desired time</span>
<span class="sd">levels. (The simplest methods just takes one step between the</span>
<span class="sd">user-desired time levels.)</span>

<span class="sd">When wrapping solvers in external software, it is occasionally not</span>
<span class="sd">feasible to implement ``advance`` because one wants to rely on the</span>
<span class="sd">software&#39;s ability to solve the whole ODE problem. Then it is more</span>
<span class="sd">natural to write a new ``solve`` method (using ``Solver.solve`` as</span>
<span class="sd">model) and call up the solve functionality in the external</span>
<span class="sd">software. Class ``odefun_sympy`` provides an example. On the other</span>
<span class="sd">hand, the wrappers for the ``scipy`` solvers (``vode`` for instance)</span>
<span class="sd">applies ``solve`` from the present package and the ``scipy`` functions</span>
<span class="sd">for doing one (adaptive) time step, called in the ``advance`` method.</span>

<span class="sd">&#39;&#39;&#39;</span>

<span class="kn">import</span> <span class="nn">pprint</span><span class="o">,</span> <span class="nn">sys</span><span class="o">,</span> <span class="nn">os</span><span class="o">,</span> <span class="nn">inspect</span>
<span class="kn">import</span> <span class="nn">numpy</span> <span class="kn">as</span> <span class="nn">np</span>

<span class="c"># Collection of all possible parameters in all solvers in this package</span>
<span class="c"># (their order is determined by the _optional_parameters and</span>
<span class="c"># _required_parameters lists in the solver classes)</span>

<span class="n">_parameters</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>

    <span class="n">f</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Right-hand side ``f(u,t)`` defining the ODE.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">f_args</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Extra positional arguments to f: ``f(u, t, *f_args, **f_kwargs).``&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">tuple</span><span class="p">,</span> <span class="nb">list</span><span class="p">,</span> <span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">),</span>
        <span class="n">default</span><span class="o">=</span><span class="p">()),</span>

    <span class="n">f_kwargs</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Extra keyword arguments to f: ``f(u, t, *f_args, **f_kwargs)``.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">dict</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="p">{}),</span>

    <span class="n">complex_valued</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;True if f is complex valued.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="bp">False</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">bool</span><span class="p">),</span>

    <span class="n">jac</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Jacobian of right-hand side function f (df/du).&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="bp">None</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">jac_args</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Extra positional arguments to jac: ``jac(u, t, *jac_args,&#39;</span>\
             <span class="s">&#39;**jac_kwargs)``.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">tuple</span><span class="p">,</span><span class="nb">list</span><span class="p">),</span>
        <span class="n">default</span><span class="o">=</span><span class="p">()),</span>

    <span class="n">jac_kwargs</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Extra keyword arguments to jac: ``jac(u, t, *jac_args,&#39;</span>\
             <span class="s">&#39;**jac_kwargs)``.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">dict</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="p">{}),</span>

    <span class="n">h_in_fd_jac</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;h in finite difference approximation of the Jacobian.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">1E-4</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">verbose</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Integer reflecting output of intermediate quantities.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mi">0</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">),</span>

    <span class="n">disk_storage</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Indicates whether u is stored in memory or in file. &#39;</span>\
             <span class="s">&#39;If string, it is the filename; if False or &quot;&quot;, u is &#39;</span>\
             <span class="s">&#39;kept in memory; if True, a default filename tmp_odspy.dat &#39;</span>\
             <span class="s">&#39;is used.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="bp">False</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">str</span><span class="p">,</span><span class="nb">bool</span><span class="p">)),</span>

    <span class="n">u_exact</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Function of t returning exact solution.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="bp">None</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">start_method</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Method for the first steps in multi-step solvers.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="s">&#39;RK2&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">str</span><span class="p">),</span>

    <span class="n">nonlinear_solver</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Newton or Picard nonlinear solver.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="s">&#39;Picard&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">str</span><span class="p">,</span>
        <span class="nb">range</span><span class="o">=</span><span class="p">(</span><span class="s">&#39;Newton&#39;</span><span class="p">,</span> <span class="s">&#39;Picard&#39;</span><span class="p">)),</span>

    <span class="n">eps_iter</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Max error measure in nonlinear solver&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">1E-4</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">max_iter</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Max no of iterations in nonlinear solver&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mi">25</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">),</span>

    <span class="n">g</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Constraint function of (u, t) in differential-algebraic systems.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">ng</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;No of components in constraint function g.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">),</span>

    <span class="n">theta</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Weight in [0,1] used for &quot;theta-rule&quot; finite difference approx.&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">0.5</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span><span class="nb">float</span><span class="p">),</span>
        <span class="nb">range</span><span class="o">=</span><span class="p">[</span><span class="mi">0</span><span class="p">,</span> <span class="mi">1</span><span class="p">]),</span>

    <span class="c"># Parameters for adaptive methods</span>

    <span class="n">atol</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Absolute tolerance for solution.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">float</span><span class="p">,</span><span class="nb">list</span><span class="p">,</span><span class="nb">tuple</span><span class="p">,</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">),</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">1E-8</span><span class="p">),</span>

    <span class="n">rtol</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Relative tolerance for solution.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">list</span><span class="p">,</span><span class="nb">tuple</span><span class="p">,</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">,</span><span class="nb">float</span><span class="p">),</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">1E-6</span><span class="p">),</span>

    <span class="n">min_step</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Minimum step size for an adaptive algorithm.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">max_step</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Maximum step size for an adaptive algorithm.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">first_step</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Suggested first time step size for an adaptive algorithm.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">solver</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Name of solver class in solvers that need an extra solver &#39;</span>\
             <span class="s">&#39;(e.g., AdaptiveResidual).&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="s">&#39;RK4&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">str</span><span class="p">),</span>

    <span class="n">butcher_tableau</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;2d-array which contains the butcher table for user-supplied &#39;</span>\
             <span class="s">&#39;Runge-Kutta method. (n,n) array for 1-level Runge-Kutta &#39;</span>\
             <span class="s">&#39;methods.(n+1,n) array for 2-level Runge-Kutta methods.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">),</span>

    <span class="c"># vode parameters</span>
    <span class="n">adams_or_bdf</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Method in vode or solvers in odepack: &quot;adams&quot; or &quot;bdf&quot;.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">str</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="s">&#39;adams&#39;</span><span class="p">,</span>
        <span class="nb">range</span><span class="o">=</span><span class="p">[</span><span class="s">&#39;adams&#39;</span><span class="p">,</span> <span class="s">&#39;bdf&#39;</span><span class="p">]),</span>

    <span class="n">order</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Maximum order used by the integrator &#39;</span>\
             <span class="s">&#39;(&lt;= 12 for &quot;adams&quot;, &lt;= 5 for &quot;bdf&quot;).&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mi">4</span><span class="p">),</span>

    <span class="n">nsteps</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Max no of internal solver steps per time step.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mi">1000</span><span class="p">),</span>

    <span class="n">method_order</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Method order for user-defined method if known.&#39;</span>\
             <span class="s">&#39;A integer for 1-level methods, or a pair of   &#39;</span>\
             <span class="s">&#39;integer for 2-levels methods.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">int</span><span class="p">,</span><span class="nb">tuple</span><span class="p">,</span><span class="nb">list</span><span class="p">,</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">)),</span>

    <span class="c"># beta, ifactor and dfactor are intended for adaptive Dormand&amp;Prince</span>
    <span class="c"># methods like dopri5 or dop853 in scipy</span>
    <span class="n">beta</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Beta argument for stabilized step size control in &#39;</span>\
             <span class="s">&#39;Dormand&amp;Prince methods from scipy&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">ifactor</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Maximum factor for increasing the step size&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mi">2</span><span class="p">),</span>

    <span class="n">dfactor</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Maximum factor for decreasing the step size&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">0.5</span><span class="p">),</span>

    <span class="n">safety</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Safety factor on new step selection&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">0.9</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="c"># odelab parameters</span>
    <span class="n">odelab_solver</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Name of Solver class in odelab&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="s">&#39;RungeKutta4&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">str</span><span class="p">),</span>

    <span class="c"># Vode_PyDS parameters</span>
    <span class="n">init_step</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Fixed step size for time mesh.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>

    <span class="n">strictdt</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Uniform time mesh vs exact dt spacings&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">bool</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="bp">True</span><span class="p">),</span>

    <span class="n">stiff</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Boolean flag to indicate stiffness.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">bool</span><span class="p">),</span>

    <span class="n">use_special</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Switch for using special times&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">bool</span><span class="p">),</span>

    <span class="n">specialtimes</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;List of special times to use during iteration&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="k">lambda</span> <span class="n">float_seq</span><span class="p">:</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> \
                     <span class="nb">isinstance</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="nb">float</span><span class="p">),</span><span class="n">float_seq</span><span class="p">))</span><span class="o">.</span><span class="n">all</span><span class="p">()),</span>

    <span class="n">ode_method</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;solver type: &quot;adams&quot; or &quot;bdf&quot;&#39;</span><span class="p">,</span>
        <span class="n">alias</span><span class="o">=</span><span class="s">&#39;method&#39;</span><span class="p">,</span>   <span class="c"># Different name in scipy.ode.vode</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">str</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="s">&#39;adams&#39;</span><span class="p">,</span>
        <span class="nb">range</span><span class="o">=</span><span class="p">(</span><span class="s">&#39;adams&#39;</span><span class="p">,</span><span class="s">&#39;bdf&#39;</span><span class="p">)),</span>

    <span class="n">relaxation</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;relaxation argument (r): new_solution = r*solution + &#39;</span>\
             <span class="s">&#39;(1-r)*old_solution&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mf">1.0</span><span class="p">,</span> <span class="nb">type</span><span class="o">=</span><span class="nb">float</span><span class="p">),</span>


    <span class="c"># parameters for Jacobian</span>
    <span class="n">jac_banded</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&quot;&quot;&quot;</span><span class="se">\</span>
<span class="s">Banded Jacobian matrix: ``jac_banded(u, t, ml, mu)``.</span>
<span class="s">``ml`` and ``mu`` are the number of lower and upper</span>
<span class="s">diagonals. The returned rectangular array should have</span>
<span class="s">shape ``neq, ml+mu+1``.&quot;&quot;&quot;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">jac_constant</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Flag to show whether Jacobian is constant, 0 (false) or 1 (true)&#39;</span><span class="p">,</span>
        <span class="n">default</span><span class="o">=</span><span class="mi">0</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">),</span>

    <span class="c"># parameters for linearly implicit ODE solvers: Lsodi, Lsoibt, Lsodis</span>
    <span class="n">res</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;User-supplied function to calculate the residual vector,&#39;</span>\
             <span class="s">&#39;defined by ``r = g(t,y) - A(t,y) * s``.&#39;</span>\
             <span class="s">&#39;Used in Lsodi, Lsoibt, Lsodis&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">ydoti</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Real array for the initial value of dy/dt.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">list</span><span class="p">,</span><span class="nb">tuple</span><span class="p">,</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">),</span>
        <span class="n">extra_check</span><span class="o">=</span><span class="k">lambda</span> <span class="n">float_seq</span><span class="p">:</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> \
             <span class="nb">isinstance</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="nb">float</span><span class="p">),</span><span class="n">float_seq</span><span class="p">))</span><span class="o">.</span><span class="n">all</span><span class="p">(),</span>
        <span class="n">default</span> <span class="o">=</span> <span class="p">[]),</span>

    <span class="c"># ja, ia, jc &amp; ic are used to describe the sparse structure</span>
    <span class="c"># of matrices</span>
    <span class="n">ja</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Integer array containing the row indices of nonzero entries &#39;</span>
              <span class="s">&#39;in a sparse matrix (CRS storage scheme).&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">list</span><span class="p">,</span><span class="nb">tuple</span><span class="p">,</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">)),</span>

    <span class="n">ia</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Integer array containing info where the different rows &#39;</span>\
              <span class="s">&#39;of a sparse matrix start (CRS storage scheme).&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="p">(</span><span class="nb">list</span><span class="p">,</span><span class="nb">tuple</span><span class="p">,</span><span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">)),</span>

    <span class="c"># ml, mu describe banded Jacobian matrix.</span>
    <span class="n">ml</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Number of lower non-zero diagonals in a banded Jacobian.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">),</span>

    <span class="n">mu</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Number of upper non-zero diagonals in a banded Jacobian.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">),</span>

    <span class="c"># mb, nb describe the block-tridiagonal form of matrix.</span>
    <span class="c"># Used in Lsoibt.</span>
    <span class="n">mb</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Block size,  mb&gt;=1, mb*nb = neq (number of equations).&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span>
        <span class="n">extra_check</span><span class="o">=</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span> <span class="n">x</span><span class="o">&gt;=</span><span class="mi">1</span><span class="p">),</span>

    <span class="n">nb</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Number of blocks in the main diagonal. nb&gt;=4.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">int</span><span class="p">,</span>
        <span class="n">extra_check</span><span class="o">=</span><span class="k">lambda</span> <span class="n">x</span><span class="p">:</span><span class="n">x</span><span class="o">&gt;=</span><span class="mi">4</span><span class="p">),</span>


   <span class="c"># Fortran versions of f, jac, g (can be used when solver is in Fortran)</span>
    <span class="n">f_f77</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Fortran subroutine for f.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">g_f77</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Fortran subroutine for g.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">jac_f77</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;Fortran subroutine for jac.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="n">myadvance</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
        <span class="n">help</span><span class="o">=</span><span class="s">&#39;User supplied function to advance current solution&#39;</span>\
             <span class="s">&#39; one step forward. See documents of class MySolver.&#39;</span><span class="p">,</span>
        <span class="nb">type</span><span class="o">=</span><span class="nb">callable</span><span class="p">),</span>

    <span class="p">)</span>

<div class="viewcode-block" id="compile_f77"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.compile_f77">[docs]</a><span class="k">def</span> <span class="nf">compile_f77</span><span class="p">(</span><span class="o">*</span><span class="n">function_strings</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Compile a list of strings, each string containing a Fortran 77</span>
<span class="sd">    subroutine (typically for f, jac, etc.).</span>
<span class="sd">    Return the extension module if keyword argument</span>
<span class="sd">    `return_module=True`, otherwise return the subroutines/functions</span>
<span class="sd">    corresponding to the given strings (default).</span>
<span class="sd">    The name of the extension module is ``tmp_callback`` and the</span>
<span class="sd">    corresponding file (to be cleaned up) is ``tmp_callback.so``.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">return_module</span> <span class="o">=</span> <span class="n">kwargs</span><span class="o">.</span><span class="n">get</span><span class="p">(</span><span class="s">&#39;return_module&#39;</span><span class="p">,</span> <span class="bp">False</span><span class="p">)</span>

    <span class="n">string_to_compile</span> <span class="o">=</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">function_strings</span><span class="p">)</span>
    <span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">f2py</span>
    <span class="n">f2py</span><span class="o">.</span><span class="n">compile</span><span class="p">(</span><span class="n">string_to_compile</span><span class="p">,</span> <span class="n">modulename</span><span class="o">=</span><span class="s">&#39;tmp_callback&#39;</span><span class="p">,</span> <span class="n">verbose</span><span class="o">=</span><span class="bp">False</span><span class="p">)</span>
    <span class="kn">import</span> <span class="nn">tmp_callback</span>

    <span class="k">if</span> <span class="n">return_module</span><span class="p">:</span>
        <span class="k">return</span> <span class="n">tmp_callback</span>
    <span class="k">else</span><span class="p">:</span>
        <span class="kn">import</span> <span class="nn">re</span>
        <span class="n">routine_names</span> <span class="o">=</span> <span class="p">[]</span>
        <span class="n">cpattern</span> <span class="o">=</span> <span class="n">re</span><span class="o">.</span><span class="n">compile</span><span class="p">(</span><span class="s">r&#39;subroutine\s+([A-Za-z0-9_]+)&#39;</span><span class="p">)</span>
        <span class="k">for</span> <span class="n">s</span> <span class="ow">in</span> <span class="n">function_strings</span><span class="p">:</span>
            <span class="n">m</span> <span class="o">=</span> <span class="n">cpattern</span><span class="o">.</span><span class="n">search</span><span class="p">(</span><span class="n">s</span><span class="p">)</span>
            <span class="k">if</span> <span class="n">m</span><span class="p">:</span>
                <span class="n">routine_names</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">m</span><span class="o">.</span><span class="n">group</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span><span class="o">.</span><span class="n">strip</span><span class="p">())</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="k">raise</span> <span class="ne">SyntaxError</span><span class="p">(</span>
                    <span class="s">&#39;Could not extract subroutine name from</span><span class="se">\n</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="n">s</span><span class="p">)</span>

        <span class="n">r</span> <span class="o">=</span> <span class="p">[</span><span class="nb">eval</span><span class="p">(</span><span class="s">&#39;tmp_callback.&#39;</span> <span class="o">+</span> <span class="n">name</span><span class="p">)</span> <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">routine_names</span><span class="p">]</span>
        <span class="k">return</span> <span class="n">r</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">r</span><span class="p">)</span> <span class="o">==</span> <span class="mi">1</span> <span class="k">else</span> <span class="n">t</span>

</div>
<span class="k">def</span> <span class="nf">_format_parameters_table</span><span class="p">(</span><span class="n">parameter_names</span><span class="p">,</span> <span class="n">fixed_width</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Make a table of parameter names and their descriptions.</span>
<span class="sd">    The parameter_names list contains the names and the</span>
<span class="sd">    descriptions are taken from _parameters[name][&#39;help&#39;].</span>
<span class="sd">    max_name_length is the width of the first column, taken</span>
<span class="sd">    as the longest name in parameter_names if not specified.</span>

<span class="sd">    The table is formatted as a simple reST table with headings</span>
<span class="sd">    (&quot;Name&quot; and &quot;Description&quot;) and three horizontal lines.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="kn">import</span> <span class="nn">textwrap</span>
    <span class="n">max_line_width</span> <span class="o">=</span> <span class="mi">71</span>

    <span class="k">if</span> <span class="n">fixed_width</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>
        <span class="n">max_name_length</span> <span class="o">=</span> <span class="nb">max</span><span class="p">([</span><span class="nb">len</span><span class="p">(</span><span class="n">name</span><span class="p">)</span> \
                               <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">parameter_names</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;Name&#39;</span><span class="p">]])</span>
        <span class="n">c1</span> <span class="o">=</span> <span class="n">max_name_length</span> <span class="o">+</span> <span class="mi">1</span>     <span class="c"># width of column 1</span>
        <span class="n">c2</span> <span class="o">=</span> <span class="p">(</span><span class="n">max_line_width</span> <span class="o">-</span> <span class="n">c1</span><span class="p">)</span>   <span class="c"># width of column 2</span>
    <span class="k">else</span><span class="p">:</span>
        <span class="n">c1</span><span class="p">,</span> <span class="n">c2</span> <span class="o">=</span> <span class="n">fixed_width</span>

    <span class="n">s</span> <span class="o">=</span> <span class="s">&#39;&#39;</span>  <span class="c"># string to be returned (table)</span>
    <span class="n">hrule</span> <span class="o">=</span> <span class="s">&#39;=&#39;</span><span class="o">*</span><span class="n">c1</span> <span class="o">+</span> <span class="s">&#39; &#39;</span> <span class="o">+</span> <span class="s">&#39;=&#39;</span><span class="o">*</span><span class="n">c2</span> <span class="o">+</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span>
    <span class="n">heading</span> <span class="o">=</span> <span class="s">&#39;Name&#39;</span> <span class="o">+</span> <span class="s">&#39; &#39;</span><span class="o">*</span><span class="p">(</span><span class="n">c1</span><span class="o">-</span><span class="mi">3</span><span class="p">)</span> <span class="o">+</span> <span class="s">&#39;Description</span><span class="se">\n</span><span class="s">&#39;</span>
    <span class="n">s</span> <span class="o">+=</span> <span class="n">hrule</span> <span class="o">+</span> <span class="n">heading</span> <span class="o">+</span> <span class="n">hrule</span>

    <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">parameter_names</span><span class="p">:</span>
        <span class="n">s</span> <span class="o">+=</span> <span class="s">&#39;</span><span class="si">%%</span><span class="s">-</span><span class="si">%d</span><span class="s">s&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">c1</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="o">%</span> <span class="n">name</span>
        <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">_parameters</span><span class="p">:</span>
            <span class="n">text</span> <span class="o">=</span> <span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;help&#39;</span><span class="p">]</span>
            <span class="k">if</span> <span class="s">&#39;default&#39;</span> <span class="ow">in</span> <span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">]:</span>
                <span class="n">text</span> <span class="o">+=</span> <span class="s">&#39; (default: </span><span class="si">%s</span><span class="s">)&#39;</span> <span class="o">%</span> <span class="nb">str</span><span class="p">(</span><span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;default&#39;</span><span class="p">])</span>
            <span class="c"># List of wrapped lines</span>
            <span class="k">if</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">text</span><span class="p">:</span>
                <span class="n">text</span> <span class="o">=</span> <span class="n">textwrap</span><span class="o">.</span><span class="n">wrap</span><span class="p">(</span><span class="n">text</span><span class="p">,</span> <span class="n">c2</span><span class="p">,</span> <span class="n">break_long_words</span><span class="o">=</span><span class="bp">False</span><span class="p">)</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="c"># Multi-line help string: keep text as is (often computer code)</span>
                <span class="n">text</span> <span class="o">=</span> <span class="n">text</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()</span>
            <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="n">text</span><span class="p">)):</span>   <span class="c"># add initial space for line 2, ...</span>
                <span class="n">text</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="s">&#39; &#39;</span><span class="o">*</span><span class="p">(</span><span class="n">c1</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="n">text</span><span class="p">[</span><span class="n">i</span><span class="p">]</span>
            <span class="n">text</span> <span class="o">=</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">text</span><span class="p">)</span>
            <span class="n">s</span> <span class="o">+=</span> <span class="n">text</span>
        <span class="n">s</span> <span class="o">+=</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span>

    <span class="n">s</span> <span class="o">+=</span> <span class="n">hrule</span>
    <span class="k">return</span> <span class="n">s</span>

<div class="viewcode-block" id="table_of_parameters"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.table_of_parameters">[docs]</a><span class="k">def</span> <span class="nf">table_of_parameters</span><span class="p">(</span><span class="n">classname</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Return a table (in reST format) of the required parameters</span>
<span class="sd">    in a class and a table of the optional parameters.</span>
<span class="sd">    The returned string is typially appended to the doc string of</span>
<span class="sd">    a solver class so that the user can easily see which parameters</span>
<span class="sd">    that must and can be provided.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">req_prm</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="n">classname</span><span class="p">,</span> <span class="s">&#39;_required_parameters&#39;</span><span class="p">)</span>
    <span class="n">opt_prm</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="n">classname</span><span class="p">,</span> <span class="s">&#39;_optional_parameters&#39;</span><span class="p">)</span>
    <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">opt_prm</span><span class="p">:</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">_parameters</span><span class="p">:</span>
            <span class="k">print</span> <span class="s">&#39;Parameter &quot;</span><span class="si">%s</span><span class="s">&quot; used in class </span><span class="si">%s</span><span class="s"> is not registered in _parameters.&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">classname</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>
            <span class="k">print</span> <span class="s">&#39;Do that before proceeding.&#39;</span>
            <span class="n">sys</span><span class="o">.</span><span class="n">exit</span><span class="p">(</span><span class="mi">1</span><span class="p">)</span>

    <span class="n">s</span> <span class="o">=</span> <span class="s">&quot;&quot;&quot;</span>
<span class="s">Required input arguments:</span>

<span class="s">&quot;&quot;&quot;</span> <span class="o">+</span> <span class="n">_format_parameters_table</span><span class="p">(</span><span class="n">req_prm</span><span class="p">)</span> <span class="o">+</span> \
<span class="sd">&quot;&quot;&quot;</span>
<span class="sd">Optional input arguments:</span>

<span class="sd">&quot;&quot;&quot;</span> <span class="o">+</span> <span class="n">_format_parameters_table</span><span class="p">(</span><span class="n">opt_prm</span><span class="p">)</span>
    <span class="c"># Add indent:</span>
    <span class="n">indent</span> <span class="o">=</span> <span class="mi">4</span>
    <span class="n">newlines</span> <span class="o">=</span> <span class="p">[</span><span class="s">&#39; &#39;</span><span class="o">*</span><span class="n">indent</span> <span class="o">+</span> <span class="n">line</span> <span class="k">for</span> <span class="n">line</span> <span class="ow">in</span> <span class="n">s</span><span class="o">.</span><span class="n">splitlines</span><span class="p">()]</span>
    <span class="n">s</span> <span class="o">=</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">newlines</span><span class="p">)</span>
    <span class="k">return</span> <span class="n">s</span>
</div>
<div class="viewcode-block" id="typeset_toc"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.typeset_toc">[docs]</a><span class="k">def</span> <span class="nf">typeset_toc</span><span class="p">(</span><span class="n">toc</span><span class="p">):</span>
    <span class="n">toc</span> <span class="o">=</span> <span class="nb">sorted</span><span class="p">(</span><span class="n">toc</span><span class="p">)</span>
    <span class="n">column1_width</span> <span class="o">=</span> <span class="nb">max</span><span class="p">([</span><span class="nb">len</span><span class="p">(</span><span class="n">classname</span><span class="p">)</span> <span class="k">for</span> <span class="n">classname</span><span class="p">,</span> <span class="n">descr</span> <span class="ow">in</span> <span class="n">toc</span><span class="p">])</span>
    <span class="n">column2_width</span> <span class="o">=</span> <span class="nb">max</span><span class="p">([</span><span class="nb">len</span><span class="p">(</span><span class="n">descr</span><span class="p">)</span>     <span class="k">for</span> <span class="n">classname</span><span class="p">,</span> <span class="n">descr</span> <span class="ow">in</span> <span class="n">toc</span><span class="p">])</span>
    <span class="n">hrule</span> <span class="o">=</span> <span class="s">&#39;=&#39;</span><span class="o">*</span><span class="p">(</span><span class="n">column1_width</span> <span class="o">+</span> <span class="mi">1</span><span class="p">)</span> <span class="o">+</span> <span class="s">&#39; &#39;</span> <span class="o">+</span> <span class="s">&#39;=&#39;</span><span class="o">*</span><span class="p">(</span><span class="n">column2_width</span><span class="p">)</span>
    <span class="k">def</span> <span class="nf">line</span><span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">descr</span><span class="p">):</span>
        <span class="k">return</span> <span class="s">&#39;</span><span class="si">%%</span><span class="s">-</span><span class="si">%d</span><span class="s">s </span><span class="si">%%</span><span class="s">s&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">column1_width</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span> <span class="o">%</span> <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">descr</span><span class="p">)</span>
    <span class="n">lines</span> <span class="o">=</span> <span class="p">[</span><span class="n">hrule</span><span class="p">,</span> <span class="n">line</span><span class="p">(</span><span class="s">&#39;Classname&#39;</span><span class="p">,</span> <span class="s">&#39;Short description&#39;</span><span class="p">),</span> <span class="n">hrule</span><span class="p">]</span> <span class="o">+</span> \
            <span class="p">[</span><span class="n">line</span><span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">descr</span><span class="p">)</span> <span class="k">for</span> <span class="n">name</span><span class="p">,</span> <span class="n">descr</span> <span class="ow">in</span> <span class="n">toc</span><span class="p">]</span> <span class="o">+</span> <span class="p">[</span><span class="n">hrule</span><span class="p">]</span>
    <span class="k">return</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">lines</span><span class="p">)</span>


</div>
<div class="viewcode-block" id="Solver"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver">[docs]</a><span class="k">class</span> <span class="nc">Solver</span><span class="p">:</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Superclass for numerical methods solving ODE problem</span>

<span class="sd">      u&#39;(t) = f(u, t),  u(0) = U0</span>

<span class="sd">    where u and U0 are scalars (for scalar ODEs) or vectors</span>
<span class="sd">    (for systems of ODEs).</span>

<span class="sd">    Attributes stored in this class:</span>

<span class="sd">    =========  ========================================================</span>
<span class="sd">    Name       Description</span>
<span class="sd">    =========  ========================================================</span>
<span class="sd">    u          array of point values of the solution function</span>
<span class="sd">    t          array of time values: u[i] corresponds to t[i]</span>
<span class="sd">    n          the most recently computed solution is u[n+1]</span>
<span class="sd">    f          function wrapping the user&#39;s right-hand side f(u, t),</span>
<span class="sd">               used in all algorithms</span>
<span class="sd">    users_f    the user&#39;s original function implementing f(u, t)</span>
<span class="sd">    PRM        an attribute for each optional and required parameter</span>
<span class="sd">    =========  ========================================================</span>

<span class="sd">    &quot;&quot;&quot;</span>

    <span class="n">_required_parameters</span> <span class="o">=</span> <span class="p">[</span><span class="s">&#39;f&#39;</span><span class="p">,]</span>
    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="p">[</span><span class="s">&#39;f_args&#39;</span><span class="p">,</span> <span class="s">&#39;f_kwargs&#39;</span><span class="p">,</span> <span class="s">&#39;complex_valued&#39;</span><span class="p">,</span>
                            <span class="s">&#39;disk_storage&#39;</span><span class="p">,</span> <span class="s">&#39;verbose&#39;</span><span class="p">,</span> <span class="s">&#39;u_exact&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="Solver.__init__"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.__init__">[docs]</a>    <span class="k">def</span> <span class="nf">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        ``f`` is the right-hand side function of the ODE u&#39; = f(u,t).</span>
<span class="sd">        The legal keyword arguments (in ``kwargs``) are documented in</span>
<span class="sd">        the tables in the doc string of this class. The ``f`` function</span>
<span class="sd">        must return a ``float`` or ``complex`` object in case of a</span>
<span class="sd">        scalar ODE and a list or array of ``float`` or ``complex`` objects</span>
<span class="sd">        in case of a system of ODEs.</span>

<span class="sd">        This constructor makes a dictionary ``self._parameters``</span>
<span class="sd">        holding all the required and optional parameters for this solver</span>
<span class="sd">        (fetched from the global ``_parameters`` dictionary in this module).</span>
<span class="sd">        The method ``adjust_parameters`` (implemented in subclasses)</span>
<span class="sd">        is called to adjust default parameter settings if needed.</span>
<span class="sd">        Then all keys in ``self._parameters`` become class attributes,</span>
<span class="sd">        filled with default values. Thereafter, all keyword arguments</span>
<span class="sd">        (in ``kwargs``) with ``None`` as value are removed as keyword</span>
<span class="sd">        arguments. The next step is to call ``set(**kwargs)``, i.e.,</span>
<span class="sd">        use the keyword arguments to modify the values of the attributes</span>
<span class="sd">        that represent the parameters in this solver. Finally, the</span>
<span class="sd">        constructor calls the method ``initialize`` (to be implemeneted</span>
<span class="sd">        in subclasses, e.g., for importing necessary modules for the solver).</span>

<span class="sd">        Instead of supplying keyword arguments to this constructor, the</span>
<span class="sd">        user can at any time call the ``set`` method with keyword</span>
<span class="sd">        arguments in order to specify parameters.</span>
<span class="sd">        &quot;&quot;&quot;</span>

        <span class="c"># self._parameters is the union of optional and required parameters</span>
        <span class="c"># for the class. self._parameters contains all the</span>
        <span class="c"># legal parameters the user of the class can set.</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
            <span class="p">(</span><span class="n">key</span><span class="p">,</span> <span class="n">value</span><span class="o">.</span><span class="n">copy</span><span class="p">())</span> <span class="k">for</span> <span class="n">key</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">_parameters</span><span class="o">.</span><span class="n">items</span><span class="p">()</span>
            <span class="k">if</span> <span class="n">key</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="ow">or</span> \
               <span class="n">key</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_required_parameters</span>
            <span class="p">)</span>

        <span class="c"># Compile user-supplied functions if they are supplied</span>
        <span class="c"># as multi-line strings in Fortran code</span>
        <span class="n">f</span><span class="p">,</span> <span class="n">kwargs</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">compile_string_functions</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>

        <span class="c"># Adjust self._parameters</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">adjust_parameters</span><span class="p">()</span>

        <span class="c"># Set default values for all parameters, remove all parameters</span>
        <span class="c"># with value None, and then apply set() to all the user-provided</span>
        <span class="c"># parameters in kwargs</span>

        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">:</span>
            <span class="k">if</span> <span class="s">&#39;default&#39;</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">]:</span>
                <span class="nb">setattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;default&#39;</span><span class="p">])</span>

        <span class="n">nones</span> <span class="o">=</span> <span class="p">[</span><span class="n">name</span> <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">kwargs</span><span class="o">.</span><span class="n">keys</span><span class="p">()</span> <span class="k">if</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">]</span>
        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">nones</span><span class="p">:</span>
            <span class="k">del</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">]</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">set</span><span class="p">(</span><span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>

        <span class="c"># Wrap user-supplied f with extra arguments</span>
        <span class="k">if</span> <span class="n">f</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">users_f</span> <span class="o">=</span> <span class="n">f</span>  <span class="c"># stored in case it is handy to have</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="nb">callable</span><span class="p">(</span><span class="n">f</span><span class="p">):</span>
                <span class="k">raise</span> <span class="ne">TypeError</span><span class="p">(</span><span class="s">&#39;f is </span><span class="si">%s</span><span class="s">, not a callable function&#39;</span> <span class="o">%</span> <span class="nb">type</span><span class="p">(</span><span class="n">f</span><span class="p">))</span>
            <span class="c"># For ODE systems, f will often return a list, but</span>
            <span class="c"># arithmetic operations with f in numerical methods</span>
            <span class="c"># require that f is an array. Let self.f be a function</span>
            <span class="c"># that first calls f(u,t) and then ensures that the</span>
            <span class="c"># result is an array (without imposing any type - if</span>
            <span class="c"># U0 has integers it is detected and converted to floats</span>
            <span class="c"># to ensure float results from f).</span>
            <span class="k">if</span> <span class="s">&#39;f_args&#39;</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_optional_parameters</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">:</span>  \
                    <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_args</span><span class="p">,</span> <span class="o">**</span><span class="bp">self</span><span class="o">.</span><span class="n">f_kwargs</span><span class="p">))</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">:</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">,</span><span class="n">t</span><span class="p">))</span>

        <span class="c"># Subclass-specific initialization</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">initialize</span><span class="p">()</span>

</div>
<div class="viewcode-block" id="Solver.compile_string_functions"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.compile_string_functions">[docs]</a>    <span class="k">def</span> <span class="nf">compile_string_functions</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Compile functions which are supplied as Fortran strings.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="n">str_funcs</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">(</span>
            <span class="p">(</span><span class="n">func</span><span class="p">,</span><span class="n">kwargs</span><span class="p">[</span><span class="n">func</span><span class="p">])</span> <span class="k">for</span> <span class="n">func</span> <span class="ow">in</span> <span class="n">kwargs</span>
            <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">kwargs</span><span class="p">[</span><span class="n">func</span><span class="p">],</span> <span class="nb">str</span><span class="p">)</span> <span class="ow">and</span> \
               <span class="p">(</span><span class="n">func</span> <span class="ow">in</span> <span class="n">_parameters</span><span class="p">)</span> <span class="ow">and</span> \
               <span class="p">(</span><span class="n">_parameters</span><span class="p">[</span><span class="n">func</span><span class="p">][</span><span class="s">&#39;type&#39;</span><span class="p">]</span> <span class="ow">is</span> <span class="nb">callable</span><span class="p">))</span>
        <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="nb">str</span><span class="p">):</span>
            <span class="n">str_funcs</span><span class="p">[</span><span class="s">&#39;f&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="n">f</span>

        <span class="k">try</span><span class="p">:</span>
            <span class="n">os</span><span class="o">.</span><span class="n">remove</span><span class="p">(</span><span class="s">&#39;_callback.so&#39;</span><span class="p">)</span>
        <span class="k">except</span><span class="p">:</span>
            <span class="k">pass</span>

        <span class="n">string_to_compile</span> <span class="o">=</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">&#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">str_funcs</span><span class="o">.</span><span class="n">values</span><span class="p">())</span>
        <span class="k">if</span> <span class="n">string_to_compile</span> <span class="ow">is</span> <span class="ow">not</span> <span class="s">&#39;&#39;</span><span class="p">:</span>
            <span class="k">try</span><span class="p">:</span>
                <span class="c"># Compile these functions together into module callback</span>
                <span class="kn">from</span> <span class="nn">numpy</span> <span class="kn">import</span> <span class="n">f2py</span>
                <span class="n">f2py</span><span class="o">.</span><span class="n">compile</span><span class="p">(</span><span class="n">string_to_compile</span><span class="p">,</span> <span class="n">modulename</span><span class="o">=</span><span class="s">&#39;_callback&#39;</span><span class="p">,</span> \
                             <span class="n">verbose</span><span class="o">=</span><span class="bp">False</span><span class="p">)</span>
                <span class="kn">import</span> <span class="nn">_callback</span>
                <span class="k">for</span> <span class="n">func</span> <span class="ow">in</span> <span class="n">str_funcs</span><span class="o">.</span><span class="n">keys</span><span class="p">():</span>
                    <span class="k">if</span> <span class="n">func</span> <span class="o">==</span> <span class="s">&#39;f&#39;</span><span class="p">:</span>
                        <span class="n">f</span> <span class="o">=</span> <span class="n">_callback</span><span class="o">.</span><span class="n">f</span>
                    <span class="k">else</span><span class="p">:</span>
                        <span class="n">kwargs</span><span class="p">[</span><span class="n">func</span><span class="p">]</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="n">_callback</span><span class="p">,</span><span class="n">func</span><span class="p">)</span>
            <span class="k">except</span><span class="p">:</span>
                <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span> <span class="s">&#39;&#39;&#39;</span>
<span class="s">           F2py failed to compile input string (=</span><span class="se">\n</span><span class="si">%s</span><span class="s">)</span>
<span class="s">           to be callable functions (</span><span class="si">%s</span><span class="s">).&#39;&#39;&#39;</span> \
                 <span class="o">%</span> <span class="p">(</span><span class="n">string_to_compile</span><span class="p">,</span> <span class="n">str_funcs</span><span class="o">.</span><span class="n">keys</span><span class="p">())</span>
        <span class="k">return</span> <span class="n">f</span><span class="p">,</span> <span class="n">kwargs</span>
</div>
<div class="viewcode-block" id="Solver.adjust_parameters"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.adjust_parameters">[docs]</a>    <span class="k">def</span> <span class="nf">adjust_parameters</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&#39;&#39;&#39;</span>
<span class="sd">        This method allows subclasses to adjust (modify or add)</span>
<span class="sd">        entries in the self._parameters dictionary.</span>
<span class="sd">        The method is called from the constructor.</span>

<span class="sd">        Further adjustments of self._parameters can be done in</span>
<span class="sd">        initialize_for_solve when all data for the solver are available.</span>
<span class="sd">        &#39;&#39;&#39;</span>
        <span class="c"># Define start_method and method here since the range depends</span>
        <span class="c"># on return value of list_all_solvers().</span>
        <span class="n">_parameters</span><span class="p">[</span><span class="s">&#39;start_method&#39;</span><span class="p">][</span><span class="s">&#39;range&#39;</span><span class="p">]</span> <span class="o">=</span> \
            <span class="n">_parameters</span><span class="p">[</span><span class="s">&#39;solver&#39;</span><span class="p">][</span><span class="s">&#39;range&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="n">list_all_solvers</span><span class="p">()</span>
        <span class="k">return</span> <span class="bp">None</span>

</div>
<div class="viewcode-block" id="Solver.initialize"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.initialize">[docs]</a>    <span class="k">def</span> <span class="nf">initialize</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Subclass-specific initialization. Called from constructor.</span>
<span class="sd">        Typical use: import modules needed in methods in the class</span>
<span class="sd">        and provide error messages if modules are not installed.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">return</span> <span class="bp">None</span>

</div>
<div class="viewcode-block" id="Solver.set"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.set">[docs]</a>    <span class="k">def</span> <span class="nf">set</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">strict</span><span class="o">=</span><span class="bp">False</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Assign values to one or more parameters, specified as keyword</span>
<span class="sd">        arguments.</span>

<span class="sd">        The legal parameters that can be set are contained in the dict</span>
<span class="sd">        self._parameters.</span>

<span class="sd">        If strict is true, only registered parameter names are accepted,</span>
<span class="sd">        otherwise unregistered parameters are ignored.</span>

<span class="sd">        The provided parameters (keyword arguments in kwargs) are</span>
<span class="sd">        first checked for legal type and legal range.</span>

<span class="sd">        Types and ranges of attributes are defined in self._parameters,</span>
<span class="sd">        which is initialized with default settings and optionally</span>
<span class="sd">        modified in the adjust_parameters method.</span>
<span class="sd">        &quot;&quot;&quot;</span>

        <span class="c"># if new string functions are supplemented</span>
        <span class="n">f_dummy</span><span class="p">,</span> <span class="n">kwargs</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">compile_string_functions</span><span class="p">(</span><span class="bp">None</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>

        <span class="c"># Check for invalid names in kwargs</span>
        <span class="n">kwargs_copy</span> <span class="o">=</span> <span class="n">kwargs</span><span class="o">.</span><span class="n">copy</span><span class="p">()</span>
        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">kwargs_copy</span><span class="p">:</span>
            <span class="k">if</span> <span class="n">name</span> <span class="ow">not</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">:</span>
                <span class="c"># invalid name</span>
                <span class="k">if</span> <span class="n">strict</span><span class="p">:</span>
                    <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&#39;set: parameter </span><span class="si">%s</span><span class="s">=</span><span class="si">%s</span><span class="s"> has illegal name&#39;</span> <span class="o">%</span> \
                                     <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">]))</span>
                <span class="k">del</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">]</span>
            <span class="k">elif</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">]</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>
                <span class="k">del</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">]</span>
                <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">):</span>    <span class="c"># Remove this attribute</span>
                    <span class="k">del</span> <span class="bp">self</span><span class="o">.</span><span class="n">__dict__</span><span class="p">[</span><span class="n">name</span><span class="p">]</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">check_input_types</span><span class="p">(</span><span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>  <span class="c"># all values of right type?</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">check_input_range</span><span class="p">(</span><span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>  <span class="c"># all values of right range?</span>

        <span class="c"># Run extra check functions if specified</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">check_extra</span><span class="p">(</span><span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>

        <span class="c"># Tests on right name/type/range were successful (if we come here)</span>
        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">kwargs</span><span class="p">:</span>
            <span class="nb">setattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">,</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">])</span>

        <span class="c"># all conditional parameters are supplied?</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">check_conditional_parameters</span><span class="p">()</span>
</div>
<div class="viewcode-block" id="Solver.check_input_types"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.check_input_types">[docs]</a>    <span class="k">def</span> <span class="nf">check_input_types</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;Check whether all existing inputs are of right specified type.&quot;&quot;&quot;</span>

        <span class="n">parameters</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span>
        <span class="n">arg_type_list</span> <span class="o">=</span> <span class="p">[(</span><span class="n">name</span><span class="p">,</span><span class="n">parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;type&#39;</span><span class="p">],</span><span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">])</span> \
                           <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">parameters</span> \
                           <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">kwargs</span> <span class="ow">and</span> \
                              <span class="s">&#39;type&#39;</span> <span class="ow">in</span> <span class="n">parameters</span><span class="p">[</span><span class="n">name</span><span class="p">]]</span>
        <span class="c"># name in parameters --&gt;  valid inputs in current class</span>
        <span class="c"># name in kwargs       --&gt;  existing inputs in current instance</span>
        <span class="c"># &#39;type&#39; in parameters[name]   --&gt; type is specified to be checked</span>

        <span class="k">for</span> <span class="n">name</span><span class="p">,</span> <span class="n">types</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">arg_type_list</span><span class="p">:</span>
            <span class="c">#(Ex: types = (callable,int)</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">types</span><span class="p">,</span> <span class="p">(</span><span class="nb">list</span><span class="p">,</span> <span class="nb">tuple</span><span class="p">)):</span>
                <span class="n">types</span> <span class="o">=</span> <span class="p">[</span><span class="n">types</span><span class="p">]</span>  <span class="c"># make a type list</span>
            <span class="n">checked_type</span> <span class="o">=</span> <span class="bp">False</span>
            <span class="k">for</span> <span class="n">tp</span> <span class="ow">in</span> <span class="n">types</span><span class="p">:</span>
                <span class="k">if</span> <span class="n">tp</span> <span class="o">==</span> <span class="nb">callable</span> <span class="ow">and</span> <span class="nb">callable</span><span class="p">(</span><span class="n">value</span><span class="p">):</span>
                    <span class="c"># value should be a callable object</span>
                    <span class="n">checked_type</span> <span class="o">=</span> <span class="bp">True</span>
                <span class="k">else</span><span class="p">:</span>
                    <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">value</span><span class="p">,</span> <span class="n">tp</span><span class="p">):</span>
                        <span class="n">checked_type</span> <span class="o">=</span> <span class="bp">True</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="n">checked_type</span><span class="p">:</span>
                <span class="k">raise</span> <span class="ne">TypeError</span><span class="p">(</span><span class="s">&#39;set: </span><span class="si">%s</span><span class="s"> is </span><span class="si">%s</span><span class="s">, not </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                                <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="nb">type</span><span class="p">(</span><span class="n">value</span><span class="p">),</span> <span class="n">types</span><span class="p">))</span>
        <span class="k">return</span> <span class="bp">True</span>

</div>
<div class="viewcode-block" id="Solver.check_input_range"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.check_input_range">[docs]</a>    <span class="k">def</span> <span class="nf">check_input_range</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span><span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;Check whether all existing inputs are in right specified range.&quot;&quot;&quot;</span>

        <span class="n">parameters</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span>
        <span class="n">arg_type_list</span> <span class="o">=</span> <span class="p">[(</span><span class="n">name</span><span class="p">,</span><span class="n">parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;range&#39;</span><span class="p">],</span><span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">])</span> \
                           <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">parameters</span> \
                           <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">kwargs</span> <span class="ow">and</span> \
                              <span class="s">&#39;range&#39;</span> <span class="ow">in</span> <span class="n">parameters</span><span class="p">[</span><span class="n">name</span><span class="p">]]</span>
        <span class="c"># name in parameters --&gt;  valid inputs in current class</span>
        <span class="c"># name in kwargs       --&gt;  existing inputs in current instance</span>
        <span class="c"># &#39;range&#39; in parameters[name]   --&gt; range is specified to be checked</span>

        <span class="k">for</span> <span class="n">name</span><span class="p">,</span> <span class="n">ranges</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">arg_type_list</span><span class="p">:</span>
            <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">value</span><span class="p">,</span> <span class="p">(</span><span class="nb">float</span><span class="p">,</span> <span class="nb">int</span><span class="p">,</span> <span class="nb">complex</span><span class="p">)):</span>
               <span class="c"># value is a comargble number</span>
                <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">ranges</span><span class="p">)</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span>  <span class="c"># ranges is an interval</span>
                    <span class="n">low</span><span class="p">,</span> <span class="n">high</span> <span class="o">=</span> <span class="n">ranges</span>
                    <span class="k">if</span> <span class="ow">not</span> <span class="p">((</span><span class="n">low</span> <span class="o">&lt;=</span> <span class="n">value</span> <span class="o">&lt;=</span> <span class="n">high</span><span class="p">)</span> <span class="ow">or</span> <span class="p">(</span><span class="n">low</span> <span class="o">&gt;=</span> <span class="n">value</span> <span class="o">&gt;=</span> <span class="n">high</span><span class="p">)):</span>
                        <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&#39;</span><span class="si">%s</span><span class="s">=</span><span class="si">%s</span><span class="s"> is illegal - range=[</span><span class="si">%s</span><span class="s">, </span><span class="si">%s</span><span class="s">]&#39;</span> <span class="o">%</span> \
                                         <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">value</span><span class="p">,</span> <span class="n">low</span><span class="p">,</span> <span class="n">high</span><span class="p">))</span>
                <span class="k">else</span><span class="p">:</span>    <span class="c"># range is a list of valid values</span>
                    <span class="k">if</span> <span class="ow">not</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">ranges</span><span class="p">:</span>
                        <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&#39;</span><span class="si">%s</span><span class="s">=</span><span class="si">%s</span><span class="s"> is illegal - range=</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                                         <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">value</span><span class="p">,</span> <span class="nb">str</span><span class="p">(</span><span class="n">ranges</span><span class="p">)))</span>
        <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="Solver.check_extra"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.check_extra">[docs]</a>    <span class="k">def</span> <span class="nf">check_extra</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        A parameter may have a keyword ``extra_check`` for user-given</span>
<span class="sd">        functions that performs consistency checks on the parameter.</span>
<span class="sd">        This method runs the user-given function(s) on the relevant</span>
<span class="sd">        set of parameters.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="n">p</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span>
        <span class="n">prm_type_list</span> <span class="o">=</span> <span class="p">[(</span><span class="n">name</span><span class="p">,</span> <span class="n">p</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;extra_check&#39;</span><span class="p">],</span> <span class="n">kwargs</span><span class="p">[</span><span class="n">name</span><span class="p">])</span> \
                         <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">p</span> \
                         <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">kwargs</span> <span class="ow">and</span> \
                         <span class="s">&#39;extra_check&#39;</span> <span class="ow">in</span> <span class="n">p</span><span class="p">[</span><span class="n">name</span><span class="p">]]</span>
        <span class="c"># name in parameters --&gt;  valid inputs in current class</span>
        <span class="c"># name in kwargs       --&gt;  existing inputs in current instance</span>
        <span class="c"># &#39;extra_check&#39; in parameters[name]</span>
        <span class="c">#           --&gt; extra functions is specified to check the value</span>

        <span class="k">for</span> <span class="n">name</span><span class="p">,</span> <span class="n">check_funcs</span><span class="p">,</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">prm_type_list</span><span class="p">:</span>
            <span class="k">try</span><span class="p">:</span>
                <span class="k">if</span> <span class="ow">not</span> <span class="n">check_funcs</span><span class="p">(</span><span class="n">value</span><span class="p">):</span>  <span class="c"># Return false</span>
                    <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span><span class="s">&#39;&#39;&#39;</span>
<span class="s">        Improper value (=</span><span class="si">%s</span><span class="s">) for parameter </span><span class="si">%s</span><span class="s">.</span>
<span class="s">        Please check your input.&#39;&#39;&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">value</span><span class="p">),</span> <span class="n">name</span><span class="p">)</span>
            <span class="k">except</span><span class="p">:</span>     <span class="c"># cannot run check_function smoothly</span>
                <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span><span class="s">&#39;&#39;&#39;</span>
<span class="s">        Cannot run check function for </span><span class="si">%s</span><span class="s">=</span><span class="si">%s</span><span class="s">.</span>
<span class="s">        Please check your input.&#39;&#39;&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="nb">str</span><span class="p">(</span><span class="n">value</span><span class="p">))</span>
        <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="Solver.get"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.get">[docs]</a>    <span class="k">def</span> <span class="nf">get</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">parameter_name</span><span class="o">=</span><span class="bp">None</span><span class="p">,</span> <span class="n">print_info</span><span class="o">=</span><span class="bp">False</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Return value of specified input parameters.</span>
<span class="sd">        If parameter_name is None, return dict of all inputs.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">if</span> <span class="n">parameter_name</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>
            <span class="c"># Python v2.7 dict comprehension yields shorter code:</span>
            <span class="c"># {name: getattr(self, name) for name in self._parameters}</span>
            <span class="n">all_args</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">([(</span><span class="n">name</span><span class="p">,</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">,</span> <span class="bp">None</span><span class="p">))</span> \
                                 <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span> \
                                 <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">)])</span>
            <span class="c"># Remove f and jac since these are wrappers of the</span>
            <span class="c"># user&#39;s functions. Instead, insert an entries that</span>
            <span class="c"># reflect the name of user-supplied functions</span>
            <span class="k">del</span> <span class="n">all_args</span><span class="p">[</span><span class="s">&#39;f&#39;</span><span class="p">]</span>
            <span class="n">all_args</span><span class="p">[</span><span class="s">&#39;name of f&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_f</span><span class="o">.</span><span class="n">func_name</span>
            <span class="k">if</span> <span class="s">&#39;jac&#39;</span> <span class="ow">in</span> <span class="n">all_args</span><span class="p">:</span>
                <span class="k">del</span> <span class="n">all_args</span><span class="p">[</span><span class="s">&#39;jac&#39;</span><span class="p">]</span>
                <span class="n">all_args</span><span class="p">[</span><span class="s">&#39;name of jac&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span><span class="o">.</span><span class="n">func_name</span>

            <span class="k">if</span> <span class="n">print_info</span><span class="p">:</span>
                <span class="k">print</span> <span class="n">pprint</span><span class="o">.</span><span class="n">pformat</span><span class="p">(</span><span class="n">all_args</span><span class="p">)</span>
            <span class="k">return</span> <span class="n">all_args</span>

        <span class="k">else</span><span class="p">:</span>
            <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">parameter_name</span><span class="p">):</span>
                <span class="n">value</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">parameter_name</span><span class="p">)</span>
                <span class="k">if</span> <span class="n">print_info</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&quot;</span><span class="si">%s</span><span class="s"> = </span><span class="si">%s</span><span class="s">&quot;</span> <span class="o">%</span> <span class="p">(</span><span class="n">parameter_name</span><span class="p">,</span> <span class="n">value</span><span class="p">)</span>
                <span class="k">return</span> <span class="n">value</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="k">raise</span> <span class="ne">AttributeError</span><span class="p">(</span><span class="s">&#39;Parameter </span><span class="si">%s</span><span class="s"> is not set&#39;</span> <span class="o">%</span> <span class="n">parameter_name</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="Solver.get_parameter_info"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.get_parameter_info">[docs]</a>    <span class="k">def</span> <span class="nf">get_parameter_info</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span><span class="n">print_info</span><span class="o">=</span><span class="bp">False</span><span class="p">):</span>
        <span class="sd">&#39;&#39;&#39;</span>
<span class="sd">        Return a dictionary containing all properties of all</span>
<span class="sd">        legal parameters in current subclass (i.e., the parameters</span>
<span class="sd">        in ``self._parameters``).</span>

<span class="sd">        If *print_info* is *True*, the ``self._parameters`` dict</span>
<span class="sd">        is pretty printed, otherwise it is returned.</span>
<span class="sd">        &#39;&#39;&#39;</span>
        <span class="k">if</span> <span class="n">print_info</span><span class="p">:</span>
            <span class="k">print</span> <span class="s">&#39;Legal parameters for class </span><span class="si">%s</span><span class="s"> are:&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span>
            <span class="k">print</span> <span class="n">pprint</span><span class="o">.</span><span class="n">pformat</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">)</span>
            <span class="k">return</span> <span class="bp">None</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span>
</div>
    <span class="k">def</span> <span class="nf">_print_method</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">with_f</span><span class="p">,</span> <span class="n">default</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Return &quot;classname(f=func, param1=..., param2=..., )&quot;.</span>
<span class="sd">        Skip f= if *with_f* is *False*.</span>
<span class="sd">        If *default* is False, skip param1= if the value equals</span>
<span class="sd">        the default value.</span>
<span class="sd">        (Helper method used by __str__ and __repr__.)</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="n">s</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span>
        <span class="n">args</span> <span class="o">=</span> <span class="p">[]</span>
        <span class="k">if</span> <span class="n">with_f</span> <span class="ow">and</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;users_f&#39;</span><span class="p">):</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">users_f</span><span class="p">,</span> <span class="s">&#39;__name__&#39;</span><span class="p">):</span>     <span class="c"># class instance?</span>
                <span class="n">f_name</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_f</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span>
	    <span class="k">else</span><span class="p">:</span>    <span class="c"># Ordinary functions</span>
                <span class="n">f_name</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_f</span><span class="o">.</span><span class="n">__name__</span>
	        <span class="k">if</span> <span class="n">f_name</span> <span class="o">==</span> <span class="s">&#39;&lt;lambda&gt;&#39;</span><span class="p">:</span>   <span class="c"># lambda function</span>
	  	    <span class="n">f_name</span> <span class="o">=</span> <span class="s">&#39;lambda u, t: ...&#39;</span>
            <span class="n">args</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="s">&#39;f=</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="n">f_name</span><span class="p">)</span>
        <span class="k">if</span> <span class="n">with_f</span> <span class="ow">and</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;users_jac&#39;</span><span class="p">):</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span><span class="p">,</span> <span class="s">&#39;__name__&#39;</span><span class="p">):</span>     <span class="c"># class instance?</span>
                <span class="n">f_name</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span>
	    <span class="k">else</span><span class="p">:</span>    <span class="c"># Ordinary functions</span>
                <span class="n">f_name</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span><span class="o">.</span><span class="n">__name__</span>
	        <span class="k">if</span> <span class="n">f_name</span> <span class="o">==</span> <span class="s">&#39;&lt;lambda&gt;&#39;</span><span class="p">:</span>   <span class="c"># lambda function</span>
	  	    <span class="n">f_name</span> <span class="o">=</span> <span class="s">&#39;lambda u, t: ...&#39;</span>
            <span class="n">args</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="s">&#39;jac=</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="n">f_name</span><span class="p">)</span>

        <span class="c"># form all parameters</span>
        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">:</span>
            <span class="k">if</span> <span class="n">name</span> <span class="o">!=</span> <span class="s">&#39;f&#39;</span> <span class="ow">and</span> <span class="n">name</span> <span class="o">!=</span> <span class="s">&#39;jac&#39;</span> <span class="ow">and</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">):</span>
                <span class="n">value</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">)</span>
                <span class="n">value_specified</span> <span class="o">=</span> <span class="bp">True</span> \
                    <span class="k">if</span> <span class="s">&#39;default&#39;</span> <span class="ow">not</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">]</span> \
                    <span class="k">else</span> <span class="n">value</span> <span class="o">!=</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;default&#39;</span><span class="p">]</span>
                <span class="k">if</span> <span class="n">default</span> <span class="ow">or</span> <span class="n">value_specified</span><span class="p">:</span>
                    <span class="n">types</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;type&#39;</span><span class="p">]</span>
                    <span class="k">if</span> <span class="n">types</span> <span class="ow">in</span> <span class="p">(</span><span class="nb">callable</span><span class="p">,</span> <span class="p">(</span><span class="nb">str</span><span class="p">,</span> <span class="nb">callable</span><span class="p">)):</span>
                        <span class="n">value</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="n">value</span><span class="p">,</span> <span class="s">&#39;__name__&#39;</span><span class="p">,</span>
                                        <span class="n">value</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>
                    <span class="k">if</span> <span class="n">name</span><span class="o">.</span><span class="n">endswith</span><span class="p">(</span><span class="s">&#39;_f77&#39;</span><span class="p">)</span> <span class="ow">and</span> <span class="n">value</span> <span class="o">==</span> <span class="s">&#39;&lt;lambda&gt;&#39;</span><span class="p">:</span>
                        <span class="c"># wrapper of Fortran functions</span>
                        <span class="k">pass</span>
                    <span class="k">else</span><span class="p">:</span>
                        <span class="n">args</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="s">&#39;</span><span class="si">%s</span><span class="s">=</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">value</span><span class="p">))</span>

        <span class="n">args</span> <span class="o">=</span> <span class="s">&#39;, &#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="n">args</span><span class="p">)</span>
        <span class="n">s</span> <span class="o">+=</span> <span class="s">&#39;(</span><span class="si">%s</span><span class="s">)&#39;</span> <span class="o">%</span> <span class="n">args</span>
        <span class="k">return</span> <span class="n">s</span>

<div class="viewcode-block" id="Solver.__repr__"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.__repr__">[docs]</a>    <span class="k">def</span> <span class="nf">__repr__</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;Return solvername(f=..., param1=..., etc.).&quot;&quot;&quot;</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">_print_method</span><span class="p">(</span><span class="n">with_f</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="bp">True</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="Solver.__str__"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.__str__">[docs]</a>    <span class="k">def</span> <span class="nf">__str__</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Return solver name, plus parameters that are different from</span>
<span class="sd">        their default values.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">_print_method</span><span class="p">(</span><span class="n">with_f</span><span class="o">=</span><span class="bp">False</span><span class="p">,</span> <span class="n">default</span><span class="o">=</span><span class="bp">False</span><span class="p">)</span>

</div>
<div class="viewcode-block" id="Solver.set_initial_condition"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.set_initial_condition">[docs]</a>    <span class="k">def</span> <span class="nf">set_initial_condition</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">U0</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Function set_initial_condition() is used to set initial value of</span>
<span class="sd">        independent variables.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="c"># Test first if U0 is sequence (len(U0) possible),</span>
        <span class="c"># and use that as indicator for system of ODEs.</span>
        <span class="c"># The below code should work for U0 having</span>
        <span class="c"># float,int,sympy.mpmath.mpi and other objects as elements.</span>
        <span class="k">try</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">U0</span><span class="p">)</span>
            <span class="n">U0</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">U0</span><span class="p">)</span>          <span class="c"># (assume U0 is sequence)</span>
        <span class="k">except</span> <span class="ne">TypeError</span><span class="p">:</span>
            <span class="c"># U0 has no __len__ method, assume as a scalar</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">=</span> <span class="mi">1</span>
            <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">U0</span><span class="p">,</span> <span class="nb">int</span><span class="p">):</span>
                <span class="n">U0</span> <span class="o">=</span> <span class="nb">float</span><span class="p">(</span><span class="n">U0</span><span class="p">)</span>           <span class="c"># avoid integer division</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">U0</span> <span class="o">=</span> <span class="n">U0</span>
</div>
<div class="viewcode-block" id="Solver.solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.solve">[docs]</a>    <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">time_points</span><span class="p">,</span> <span class="n">terminate</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Compute discrete solution u of the ODE problem at time points</span>
<span class="sd">        specified in the array time_points. An optional user-supplied</span>
<span class="sd">        function ``terminate(u, t, step_no)`` can be supplied to</span>
<span class="sd">        terminate the solution process (``terminate`` returns True</span>
<span class="sd">        or False) at some time earlier than ``time_points[-1]``.</span>

<span class="sd">        Most classes in this solver hierarchy inherit this ``solve``</span>
<span class="sd">        method and implement their special ``advance`` method to</span>
<span class="sd">        advance the solution one step.</span>
<span class="sd">        Some solver classes will implement their own ``solve``</span>
<span class="sd">        method, for instance if they wrap some underlying software</span>
<span class="sd">        that has a suitable ``solve`` functionality.</span>

<span class="sd">        The algorithm steps in this ``solve`` method goes as follows.</span>
<span class="sd">        The initialize_for_solve method is called to initialize</span>
<span class="sd">        various data needed in the solution process (self. u, for instance).</span>
<span class="sd">        Thereafter, ``validate_data`` is called to perform a consistency</span>
<span class="sd">        check on data. We are then ready for the core of the method:</span>
<span class="sd">        the time loop.</span>

<span class="sd">        Output:</span>
<span class="sd">           u            : array to hold solution values corresponding to points</span>
<span class="sd">           t            : array to hold time values.Usually same as time_points</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">if</span> <span class="n">terminate</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>    <span class="c"># Default function</span>
            <span class="n">terminate</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">step_no</span><span class="p">:</span> <span class="bp">False</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">n</span> <span class="o">=</span> <span class="mi">0</span>  <span class="c"># time step counter</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">()</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">validate_data</span><span class="p">()</span>

        <span class="c"># The time loop</span>
        <span class="n">N</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="o">.</span><span class="n">size</span> <span class="o">-</span> <span class="mi">1</span>  <span class="c"># no of intervals</span>
        <span class="k">for</span> <span class="n">n</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">N</span><span class="p">):</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">n</span> <span class="o">=</span> <span class="n">n</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">advance</span><span class="p">()</span>   <span class="c"># new value</span>

            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span> <span class="o">&gt;</span> <span class="mi">1</span><span class="p">:</span>
                <span class="k">print</span> <span class="s">&#39;</span><span class="si">%s</span><span class="s">, step </span><span class="si">%d</span><span class="s">, t=</span><span class="si">%g</span><span class="s">&#39;</span> <span class="o">%</span> \
                      <span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
            <span class="k">if</span> <span class="n">terminate</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">):</span>
                <span class="k">print</span> <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">,</span> \
                      <span class="s">&#39;terminated at t=</span><span class="si">%g</span><span class="s">&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span>
                <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
                    <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[:</span><span class="n">n</span><span class="o">+</span><span class="mi">2</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[:</span><span class="n">n</span><span class="o">+</span><span class="mi">2</span><span class="p">]</span>
                <span class="c"># else: must keep original size of file, rest is 0</span>
                <span class="k">break</span>  <span class="c"># terminate time loop over n</span>
        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">flush</span><span class="p">()</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

</div>
<div class="viewcode-block" id="Solver.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;Advance solution one time step.&quot;&quot;&quot;</span>
        <span class="k">raise</span> <span class="ne">NotImplementedError</span>

</div>
<div class="viewcode-block" id="Solver.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Setting values of internal attributes to be used in iteration.</span>

<span class="sd">        These internal attributes are ususally dependent on the values of</span>
<span class="sd">        other attributes. For example, for Rkc, self.itol should be</span>
<span class="sd">        initialized here as a flag to indicate whether self.atol is</span>
<span class="sd">        supplied as scalar or sequence.</span>

<span class="sd">        In subclasses, this function can be extended when required.</span>
<span class="sd">        &quot;&quot;&quot;</span>

        <span class="c"># Detect whether data type is in complex type or not.</span>
        <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;f&#39;</span><span class="p">):</span>
            <span class="k">try</span><span class="p">:</span>
                <span class="n">value</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">array</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">]))</span>
            <span class="k">except</span> <span class="ne">IndexError</span><span class="p">:</span>
                <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&#39;time_points array is empty - bug in its construction&#39;</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="n">value</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">)</span>
        <span class="k">if</span> <span class="n">value</span><span class="o">.</span><span class="n">dtype</span> <span class="ow">in</span> <span class="p">(</span><span class="n">np</span><span class="o">.</span><span class="n">int32</span><span class="p">,</span> <span class="n">np</span><span class="o">.</span><span class="n">int64</span><span class="p">,</span> <span class="n">np</span><span class="o">.</span><span class="n">int</span><span class="p">):</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">dtype</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">complex</span> <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">complex_valued</span> <span class="k">else</span> <span class="n">np</span><span class="o">.</span><span class="n">float</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">dtype</span> <span class="o">=</span> <span class="n">value</span><span class="o">.</span><span class="n">dtype</span>

        <span class="c"># Check that consistent self.complex_valued is given</span>
        <span class="k">if</span> <span class="nb">str</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">dtype</span><span class="p">)</span><span class="o">.</span><span class="n">startswith</span><span class="p">(</span><span class="s">&#39;complex&#39;</span><span class="p">):</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">complex_valued</span><span class="p">:</span>
                <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&quot;Solving a complex ODE, but parameter complex_valued is not set to True in the solver&#39;s constructor or set method&quot;</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">complex_valued</span><span class="p">:</span>
                <span class="k">pass</span> <span class="c"># ok, because real ODE can be complex by complex U0</span>
                <span class="c">#raise ValueError(&quot;Seemingly real-valued ODE problem, but parameter complex_valued is True&quot;)</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">_allocate_u</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)</span>
        <span class="c"># Assume that self.t[0] corresponds to self.U0</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">U0</span>

        <span class="k">return</span> <span class="bp">None</span>
</div>
    <span class="k">def</span> <span class="nf">_allocate_u</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">t_array</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Allocate storage for the solution, given the time points</span>
<span class="sd">        (in `t_array`).</span>

<span class="sd">        Other data needed for allocating the self.u array are taken</span>
<span class="sd">        from the solver instance (self.disk_storage, self.neq, self.dtype).</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">if</span> <span class="nb">isinstance</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">,</span> <span class="nb">bool</span><span class="p">)</span> <span class="ow">and</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span> <span class="o">=</span> <span class="s">&#39;tmp_odespy.dat&#39;</span>
        <span class="n">N</span> <span class="o">=</span> <span class="n">t_array</span><span class="o">.</span><span class="n">size</span> <span class="o">-</span> <span class="mi">1</span>  <span class="c"># no of intervals</span>
        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>  <span class="c"># scalar ODEs</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">memmap</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">,</span>
                                   <span class="n">dtype</span><span class="o">=</span><span class="n">data_type</span><span class="p">,</span>
                                   <span class="n">mode</span><span class="o">=</span><span class="s">&#39;w+&#39;</span><span class="p">,</span>
                                   <span class="n">shape</span><span class="o">=</span><span class="p">(</span><span class="n">N</span><span class="o">+</span><span class="mi">1</span><span class="p">,))</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">zeros</span><span class="p">(</span><span class="n">N</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">dtype</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>              <span class="c"># systems of ODEs</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">memmap</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">,</span>
                                   <span class="n">dtype</span><span class="o">=</span><span class="n">data_type</span><span class="p">,</span>
                                   <span class="n">mode</span><span class="o">=</span><span class="s">&#39;w+&#39;</span><span class="p">,</span>
                                   <span class="n">shape</span><span class="o">=</span><span class="p">(</span><span class="n">N</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">))</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">zeros</span><span class="p">((</span><span class="n">N</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">),</span> <span class="bp">self</span><span class="o">.</span><span class="n">dtype</span><span class="p">)</span>


<div class="viewcode-block" id="Solver.constant_time_step"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.constant_time_step">[docs]</a>    <span class="k">def</span> <span class="nf">constant_time_step</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;Check if self.t has a uniform partition.&quot;&quot;&quot;</span>
        <span class="k">return</span> <span class="n">np</span><span class="o">.</span><span class="n">allclose</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span>
                           <span class="n">np</span><span class="o">.</span><span class="n">linspace</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span> <span class="nb">len</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)))</span>

</div>
<div class="viewcode-block" id="Solver.validate_data"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.validate_data">[docs]</a>    <span class="k">def</span> <span class="nf">validate_data</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        This function is used for extra checking and validating of</span>
<span class="sd">        attributes before the computations start.</span>

<span class="sd">        This version checks that the ``time_points`` is correctly</span>
<span class="sd">        set up. The function also check that all required parameters</span>
<span class="sd">        are initialized. Subclass versions may introduce additional</span>
<span class="sd">        tests and help.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="c"># self.t should be a sequence of numbers</span>
        <span class="k">if</span> <span class="p">(</span><span class="ow">not</span> <span class="nb">isinstance</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="p">(</span><span class="nb">list</span><span class="p">,</span> <span class="nb">tuple</span><span class="p">,</span> <span class="n">np</span><span class="o">.</span><span class="n">ndarray</span><span class="p">)))</span> \
            <span class="ow">or</span> <span class="p">(</span><span class="ow">not</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span>
            <span class="c"># all items in self.t should be numbers</span>
            <span class="p">[</span><span class="nb">isinstance</span><span class="p">(</span><span class="n">t</span><span class="p">,</span> <span class="p">(</span><span class="nb">int</span><span class="p">,</span><span class="nb">float</span><span class="p">))</span> <span class="k">for</span> <span class="n">t</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">])</span><span class="o">.</span><span class="n">all</span><span class="p">()):</span>
                <span class="k">raise</span> <span class="ne">TypeError</span><span class="p">,</span> \
                    <span class="s">&#39;solve: time_points(=</span><span class="si">%s</span><span class="s">) is not a proper &#39;</span>\
                    <span class="s">&#39;sequence of real numbers&#39;</span> <span class="o">%</span> <span class="nb">str</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)</span>

        <span class="c"># self.t should be supplied in an asscending/descending order</span>
        <span class="n">t_sorted</span> <span class="o">=</span> <span class="nb">sorted</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="n">reverse</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">&gt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">if</span> <span class="nb">list</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)</span> <span class="o">!=</span> <span class="nb">list</span><span class="p">(</span><span class="n">t_sorted</span><span class="p">):</span>
            <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span> \
                <span class="s">&#39;time_points(=</span><span class="si">%s</span><span class="s">) is not provided in an ascending/descending&#39;</span>\
                <span class="s">&#39; order!&#39;</span> <span class="o">%</span> <span class="nb">str</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)</span>

        <span class="c"># Test whether all required parameters are provided</span>
        <span class="k">for</span> <span class="n">arg</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_required_parameters</span><span class="p">:</span>
            <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">arg</span><span class="p">):</span>
                <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span>\
                    <span class="s">&#39;&quot;</span><span class="si">%s</span><span class="s">&quot; has to be input as required parameter(s) for &#39;</span>\
                    <span class="s">&#39;solver </span><span class="si">%s</span><span class="s">.&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">arg</span><span class="p">,</span><span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>
        <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="Solver.switch_to"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.switch_to">[docs]</a>    <span class="k">def</span> <span class="nf">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">solver_target</span><span class="p">,</span> <span class="n">print_info</span><span class="o">=</span><span class="bp">False</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Create a new solver instance which switch to another subclass with</span>
<span class="sd">        same values of common attributes.</span>

<span class="sd">        `solver_target` is either as a string (class name) or</span>
<span class="sd">        a class, i.e., ``RK4`` or ``&#39;RK4&#39;``.</span>
<span class="sd">        The `kwargs` arguments are optional parameters to</span>
<span class="sd">        reset/supplement values of argmenters in the solver we switch to.</span>
<span class="sd">        The instance of the target solver is returned.</span>

<span class="sd">        Example:</span>

<span class="sd">        &gt;&gt;&gt; import odespy</span>
<span class="sd">        &gt;&gt;&gt; f = lambda u,t: -u</span>
<span class="sd">        &gt;&gt;&gt; time_points = np.linspace(0.,2.,11)</span>
<span class="sd">        &gt;&gt;&gt; exact_u = np.exp(-time_points)</span>
<span class="sd">        &gt;&gt;&gt; m1 = odespy.RK2(f)</span>
<span class="sd">        &gt;&gt;&gt; m1.set_initial_condition(1.)</span>
<span class="sd">        &gt;&gt;&gt; u1, t = m1.solve(time_points)</span>
<span class="sd">        &gt;&gt;&gt; print &#39;Normarized error with RK2 is %g&#39; % np.linalg.norm(u1 - exact_u)</span>
<span class="sd">        Normarized error with RK2 is 0.0077317</span>
<span class="sd">        &gt;&gt;&gt; m2 = m1.switch_to(odespy.RKFehlberg, rtol=1e-18)</span>
<span class="sd">        &gt;&gt;&gt; u2, t = m2.solve(time_points)</span>
<span class="sd">        &gt;&gt;&gt; print &#39;Normarized error with RKFehlberg is %g&#39; % np.linalg.norm(u2 - exact_u)</span>
<span class="sd">        Normarized error with RKFehlberg is 8.55517e-08</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="c"># Extract name list of all the subclasses in this module</span>
        <span class="n">solver_list</span> <span class="o">=</span> <span class="n">list_all_solvers</span><span class="p">()</span>
        <span class="n">error_message</span> <span class="o">=</span> <span class="s">&#39;&#39;&#39;</span>
<span class="s">        Input error! Your input </span><span class="si">%s</span><span class="s"> is not a valid solver name!</span>
<span class="s">        Valid names are </span><span class="si">%s</span><span class="s"> &#39;&#39;&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">solver_target</span><span class="p">),</span> <span class="nb">str</span><span class="p">(</span><span class="n">solver_list</span><span class="p">))</span>

        <span class="c"># Check whether input solver_target is a valid subclass of Solver</span>
        <span class="k">try</span><span class="p">:</span>
            <span class="kn">import</span> <span class="nn">odespy</span>
            <span class="k">if</span> <span class="nb">type</span><span class="p">(</span><span class="n">solver_target</span><span class="p">)</span> <span class="ow">is</span> <span class="nb">str</span><span class="p">:</span>
                <span class="c"># Convert string to class name</span>
                <span class="n">solver_target</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="n">odespy</span><span class="p">,</span> <span class="n">solver_target</span><span class="p">)</span>
        <span class="k">except</span><span class="p">:</span>
            <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span> <span class="n">error_message</span>

        <span class="k">if</span> <span class="ow">not</span> <span class="n">solver_target</span><span class="o">.</span><span class="n">__name__</span> <span class="ow">in</span> <span class="n">list_all_solvers</span><span class="p">():</span>
            <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span> <span class="n">error_message</span>



        <span class="c"># Neglect the attributes if they are illegal in target solver</span>
        <span class="n">args_dict</span> <span class="o">=</span> <span class="p">{}</span>
        <span class="c"># Extract all the existing attributes which are legal both in</span>
        <span class="c"># current solver and the target solver</span>
        <span class="n">common_attr</span> <span class="o">=</span> <span class="nb">set</span><span class="p">(</span><span class="n">solver_target</span><span class="o">.</span><span class="n">_optional_parameters</span><span class="p">)</span> <span class="o">&amp;</span> \
                      <span class="nb">set</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">_optional_parameters</span><span class="p">)</span>
        <span class="c"># Extract values of these common attributes</span>
        <span class="n">args_dict</span> <span class="o">=</span> <span class="nb">dict</span><span class="p">((</span><span class="n">name</span><span class="p">,</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">))</span> <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">common_attr</span> \
                             <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">))</span>

        <span class="c"># Exception: &#39;f&#39; is to provided as 1st parameter to initialize</span>
        <span class="c"># new instance in target solver</span>
        <span class="k">if</span> <span class="s">&#39;f&#39;</span> <span class="ow">in</span> <span class="n">kwargs</span><span class="p">:</span>    <span class="c"># f is reset as a new parameter</span>
            <span class="n">f</span> <span class="o">=</span> <span class="n">kwargs</span><span class="o">.</span><span class="n">pop</span><span class="p">(</span><span class="s">&#39;f&#39;</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="n">f</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;f&#39;</span><span class="p">,</span> <span class="bp">None</span><span class="p">)</span>  <span class="c"># the wrapped general form f(u,t)</span>
        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="p">(</span><span class="s">&#39;f_f77&#39;</span><span class="p">,</span> <span class="s">&#39;f_args&#39;</span><span class="p">,</span> <span class="s">&#39;f_kwargs&#39;</span><span class="p">,</span> <span class="s">&#39;f&#39;</span><span class="p">):</span>
            <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">args_dict</span><span class="p">:</span>
                <span class="k">del</span> <span class="n">args_dict</span><span class="p">[</span><span class="n">name</span><span class="p">]</span>

        <span class="c"># Union with new values in kwargs</span>
        <span class="c"># Note: Old values for parameters in current solver are neglected</span>
        <span class="c">#       if they are provided in kwargs.</span>
        <span class="n">args_dict</span><span class="o">.</span><span class="n">update</span><span class="p">(</span><span class="n">kwargs</span><span class="p">)</span>

        <span class="c"># Create new instance through normal constructor __init__().</span>
        <span class="c"># It ensures all the necessary checking/setting in target solver.</span>
        <span class="n">new</span> <span class="o">=</span> <span class="n">solver_target</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="o">**</span><span class="n">args_dict</span><span class="p">)</span>

        <span class="c"># Set up initial value U0 if available</span>
        <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span><span class="s">&#39;U0&#39;</span><span class="p">):</span>
            <span class="n">new</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">)</span>

        <span class="c"># Print out information if desired</span>
        <span class="k">if</span> <span class="n">print_info</span><span class="p">:</span>
            <span class="c"># neglected attributes in new solver</span>
            <span class="n">diff_args</span> <span class="o">=</span> <span class="nb">set</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">__dict__</span><span class="o">.</span><span class="n">keys</span><span class="p">())</span> <span class="o">-</span> <span class="nb">set</span><span class="p">(</span><span class="n">new</span><span class="o">.</span><span class="n">__dict__</span><span class="o">.</span><span class="n">keys</span><span class="p">())</span> \
                <span class="o">-</span> <span class="nb">set</span><span class="p">((</span><span class="s">&#39;u&#39;</span><span class="p">,</span><span class="s">&#39;t&#39;</span><span class="p">,</span><span class="s">&#39;n&#39;</span><span class="p">,</span><span class="s">&#39;dtype&#39;</span><span class="p">))</span>
            <span class="k">if</span> <span class="n">diff_args</span><span class="p">:</span>
                <span class="k">print</span> <span class="s">&#39;These attributes are neglected in </span><span class="si">%s</span><span class="s">: </span><span class="si">%s</span><span class="se">\n</span><span class="s">&#39;</span> \
                    <span class="o">%</span> <span class="p">(</span><span class="n">solver_target</span><span class="o">.</span><span class="n">__name__</span><span class="p">,</span> <span class="nb">str</span><span class="p">(</span><span class="n">diff_args</span><span class="p">)[</span><span class="mi">5</span><span class="p">:</span><span class="o">-</span><span class="mi">2</span><span class="p">])</span>
            <span class="k">print</span> <span class="s">&#39;Switched to solver </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="nb">str</span><span class="p">(</span><span class="n">solver_target</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>

        <span class="k">return</span> <span class="n">new</span>
</div>
<div class="viewcode-block" id="Solver.check_conditional_parameters"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.check_conditional_parameters">[docs]</a>    <span class="k">def</span> <span class="nf">check_conditional_parameters</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        This function is used to check whether conditional parameters are</span>
<span class="sd">        provided when specified condition fulfilled.</span>

<span class="sd">        This function is not intended for simple solvers.</span>
<span class="sd">        So it is not called automatically in current solvers.py.</span>
<span class="sd">        But for some complicated solvers as ones in ODEPACK, they</span>
<span class="sd">        are very useful and convenient.</span>

<span class="sd">        Future developers can apply these functions at appropriate</span>
<span class="sd">        locations with corresponding property-setting in</span>
<span class="sd">        adjust_parameters().</span>

<span class="sd">        For example, in Lsode_ODEPACK, when iter_method is set to 4, it</span>
<span class="sd">        indicates that ODEPACK would apply user-supplied banded Jacoabian</span>
<span class="sd">        function in corrector iteration. Then we need to confirm either</span>
<span class="sd">        &#39;jac_banded&#39; or &#39;jac_fortran&#39; is supplied. Besides, &#39;ml&#39; &amp; &#39;mu&#39; are</span>
<span class="sd">        also necessary for iteration with banded Jacobian matrix.</span>
<span class="sd">        Thus in order to confirm sufficient conditional inputs, we set</span>
<span class="sd">        parameters[&#39;iter_method&#39;][&#39;condition_list&#39;] =</span>
<span class="sd">             {...,&#39;4&#39;: ((&#39;jac_banded&#39;,&#39;jac_fortran&#39;),ml,mu),...}</span>

<span class="sd">        In this function, we would check all the legal parameters with specified</span>
<span class="sd">        condition-list, and make sure all the conditional parameters with</span>
<span class="sd">        current value is supplied.</span>

<span class="sd">        &quot;&quot;&quot;</span>
        <span class="n">parameters</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span>
        <span class="c"># Parameters with condition-list settings</span>
        <span class="n">with_condition_args</span> <span class="o">=</span> \
            <span class="p">[(</span><span class="n">name</span><span class="p">,</span> <span class="n">parameters</span><span class="p">[</span><span class="n">name</span><span class="p">][</span><span class="s">&#39;condition-list&#39;</span><span class="p">],</span> \
              <span class="nb">str</span><span class="p">(</span><span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span><span class="n">name</span><span class="p">)))</span> \
                 <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="n">parameters</span> \
                    <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">__dict__</span> <span class="ow">and</span>
                       <span class="s">&#39;condition-list&#39;</span> <span class="ow">in</span> <span class="n">parameters</span><span class="p">[</span><span class="n">name</span><span class="p">]]</span>

        <span class="c"># name in parameters   --&gt;  valid inputs for current class</span>
        <span class="c"># name in self.__dict__ --&gt;  existing inputs for curremt instance</span>
        <span class="c"># &#39;condition-list&#39; in parameters[name] --&gt;</span>
        <span class="c">#                       &#39;condition-list&#39; is specified to check</span>

        <span class="k">for</span> <span class="p">(</span><span class="n">name</span><span class="p">,</span> <span class="n">conditions</span><span class="p">,</span> <span class="n">value</span><span class="p">)</span> <span class="ow">in</span> <span class="n">with_condition_args</span><span class="p">:</span>
            <span class="c"># Ex: name = &#39;iter_method&#39;</span>
            <span class="c">#     conditions = {&#39;1&#39;:((&#39;jac&#39;,&#39;jac_f77&#39;),), &#39;4&#39;:.., &#39;5&#39;:..})</span>
            <span class="c">#     value = &#39;1&#39;</span>
            <span class="k">if</span> <span class="n">value</span> <span class="ow">in</span> <span class="n">conditions</span><span class="p">:</span>
                <span class="c"># There is conditional requirements for current value</span>
                <span class="n">condition_args</span> <span class="o">=</span> <span class="n">conditions</span><span class="p">[</span><span class="n">value</span><span class="p">]</span>
                <span class="c"># list/tuple for conditional parameters</span>
                <span class="k">for</span> <span class="n">arg</span> <span class="ow">in</span> <span class="n">condition_args</span><span class="p">:</span>
                    <span class="k">if</span> <span class="ow">not</span> <span class="nb">isinstance</span><span class="p">(</span><span class="n">arg</span><span class="p">,</span> <span class="nb">str</span><span class="p">):</span>
                        <span class="c"># arg is a list for alternative parameters</span>
                        <span class="c"># e.g. (&#39;jac&#39;, &#39;jac_f77&#39;)</span>
                        <span class="c"># Either &#39;jac&#39; or &#39;jac_f77&#39; should be supplied</span>
                        <span class="n">found</span> <span class="o">=</span> <span class="nb">bool</span><span class="p">([</span><span class="n">p_name</span> <span class="k">for</span> <span class="n">p_name</span> <span class="ow">in</span> <span class="n">arg</span> \
                                          <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span><span class="n">p_name</span><span class="p">)])</span>
                        <span class="n">arg_print</span> <span class="o">=</span> <span class="s">&#39;One of </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="nb">str</span><span class="p">(</span><span class="n">arg</span><span class="p">)</span>
                    <span class="k">else</span><span class="p">:</span>      <span class="c"># arg is a single parameter</span>
                        <span class="n">found</span> <span class="o">=</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">arg</span><span class="p">)</span>
                        <span class="n">arg_print</span> <span class="o">=</span> <span class="n">arg</span>
                    <span class="k">if</span> <span class="ow">not</span> <span class="n">found</span><span class="p">:</span>
                        <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">,</span><span class="s">&#39;&#39;&#39;</span><span class="se">\</span>
<span class="s">        Error! Unsufficient input!</span>
<span class="s">        </span><span class="si">%s</span><span class="s"> must be set when </span><span class="si">%s</span><span class="s"> is </span><span class="si">%s</span><span class="s">!&#39;&#39;&#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">arg_print</span><span class="p">,</span><span class="n">name</span><span class="p">,</span><span class="n">value</span><span class="p">)</span>
        <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="Solver.has_u_t_all"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Solver.has_u_t_all">[docs]</a>    <span class="k">def</span> <span class="nf">has_u_t_all</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Return True if self.u_all and self.t_all, defined in</span>
<span class="sd">        subclasses derived from Adaptive, are computed.</span>
<span class="sd">        This function for testing is placed in class Solver so</span>
<span class="sd">        that any class can check of intermediate time steps</span>
<span class="sd">        have been computed and are available.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;u_all&#39;</span><span class="p">)</span> <span class="ow">and</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;t_all&#39;</span><span class="p">)</span> <span class="ow">and</span> \
           <span class="nb">len</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t_all</span><span class="p">)</span> <span class="o">&gt;</span> <span class="mi">1</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">True</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="c"># Remove self.u_all and self.t_all</span>
            <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;u_all&#39;</span><span class="p">):</span> <span class="k">del</span> <span class="bp">self</span><span class="o">.</span><span class="n">u_all</span>
            <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;t_all&#39;</span><span class="p">):</span> <span class="k">del</span> <span class="bp">self</span><span class="o">.</span><span class="n">t_all</span>
            <span class="k">return</span> <span class="bp">False</span>

</div></div>
<div class="viewcode-block" id="MySolver"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MySolver">[docs]</a><span class="k">class</span> <span class="nc">MySolver</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Users can define a solver with supplying a function</span>
<span class="sd">    myadvance(), and make use of all possible parameters</span>
<span class="sd">    in this module::</span>

<span class="sd">        myadvance(MySolver_instance)  --&gt;  return u_new</span>

<span class="sd">    Example::</span>

<span class="sd">        def myadvance_(ms):</span>
<span class="sd">            f, u, t, n, atol = ms.f, ms.u, ms.t, ms.n, ms.atol</span>
<span class="sd">            # All class attributes can be obtained</span>
<span class="sd">            u_new = ...</span>
<span class="sd">            return u_new</span>

<span class="sd">        def f(u,t):</span>
<span class="sd">            udot = ...</span>
<span class="sd">            return udot</span>

<span class="sd">        method = MySolver(f, myadvance=myadvance_)</span>
<span class="sd">        method.set_initial_condition(u0)</span>
<span class="sd">        u,t = method.solve(time_points)</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">_required_parameters</span> <span class="o">=</span> <span class="p">[</span><span class="s">&#39;f&#39;</span><span class="p">,</span> <span class="s">&#39;myadvance&#39;</span><span class="p">]</span>
    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">_parameters</span><span class="o">.</span><span class="n">keys</span><span class="p">()</span>
    <span class="c"># All arguments are valid and accessible for users.</span>

<div class="viewcode-block" id="MySolver.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MySolver.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">myadvance</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>

<span class="c">### End of class Solver ###</span>
</div></div>
<div class="viewcode-block" id="ForwardEuler"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ForwardEuler">[docs]</a><span class="k">class</span> <span class="nc">ForwardEuler</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Forward Euler scheme::</span>

<span class="sd">        u[n+1] = u[n] + dt*f(u[n], t[n])</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&#39;The simple explicit (forward) Euler scheme&#39;</span>

<div class="viewcode-block" id="ForwardEuler.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ForwardEuler.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">u_new</span>
</div></div>
<span class="n">Euler</span> <span class="o">=</span> <span class="n">ForwardEuler</span>   <span class="c"># synonym</span>


<div class="viewcode-block" id="Leapfrog"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Leapfrog">[docs]</a><span class="k">class</span> <span class="nc">Leapfrog</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Leapfrog scheme::</span>

<span class="sd">        u[n+1] = u[n-1] + dt2*f(u[n], t[n])</span>

<span class="sd">    with::</span>

<span class="sd">        dt2 = t[n+1] - t[n-1]</span>

<span class="sd">    Forward Euler is used for the first step.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&#39;Standard explicit Leapfrog scheme&#39;</span>

<div class="viewcode-block" id="Leapfrog.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Leapfrog.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">1</span><span class="p">:</span>
            <span class="n">dt2</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt2</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">u_new</span>


</div></div>
<div class="viewcode-block" id="LeapfrogFiltered"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.LeapfrogFiltered">[docs]</a><span class="k">class</span> <span class="nc">LeapfrogFiltered</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    The standard Leapfrog scheme reads::</span>

<span class="sd">        u[n+1] = u[k-1] + dt2*f(u[n], t[n])</span>

<span class="sd">    with::</span>

<span class="sd">        dt2 = t[n+1] - t[k-1]</span>

<span class="sd">    Forward Euler is used for the first step.</span>
<span class="sd">    Since Leapfrog gives oscillatory solutions, this class</span>
<span class="sd">    applies a common filtering technique::</span>

<span class="sd">        u[n] = u[n] + gamma*(u[n-1] - 2*u[n] + u[n+1])</span>

<span class="sd">    with gamma=0.6 as in the NCAR Climate Model.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&#39;Filtered Leapfrog scheme&#39;</span>

<div class="viewcode-block" id="LeapfrogFiltered.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.LeapfrogFiltered.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">gamma</span> <span class="o">=</span> <span class="mf">0.6</span>  <span class="c"># NCAR Climate Model</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">1</span><span class="p">:</span>
            <span class="n">dt2</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt2</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">gamma</span><span class="o">*</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="mi">2</span><span class="o">*</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">u_new</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">u_new</span>


</div></div>
<div class="viewcode-block" id="Heun"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Heun">[docs]</a><span class="k">class</span> <span class="nc">Heun</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Heun&#39;s method, also known as an RungeKutta2 or Trapezoidal method.</span>
<span class="sd">    Basically, it is a central difference method, with one</span>
<span class="sd">    iteration and the Forward Euler scheme as start value.</span>
<span class="sd">    In this sense, it is a predictor-corrector method.</span>

<span class="sd">    Scheme::</span>

<span class="sd">        u[n+1] = u[n] + 0.5*dt*(f(u[n],t[n]) + f(u[n]+dt*f(u[n],t[n]),t[n+1]))</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Heun&#39;s explicit method (similar to RK2)&quot;</span>

<div class="viewcode-block" id="Heun.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Heun.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">u_star</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>  <span class="c"># Forward Euler step</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span> <span class="o">+</span> <span class="n">f</span><span class="p">(</span><span class="n">u_star</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]))</span>
        <span class="k">return</span> <span class="n">u_new</span>


</div></div>
<span class="n">Trapezoidal</span> <span class="o">=</span> <span class="n">Heun</span>   <span class="c"># alias for solver Heun</span>


<div class="viewcode-block" id="RK2"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK2">[docs]</a><span class="k">class</span> <span class="nc">RK2</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Standard Runge-Kutta 2nd method::</span>

<span class="sd">        u[n+1] = u[n] + dt*f(u[n] + 0.5*(dt*f(u[n],t[n])),t[n] + 0.5*dt)</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 2nd-order Runge-Kutta method&quot;</span>

<div class="viewcode-block" id="RK2.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK2.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">K1</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="n">K2</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">K1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">dt</span><span class="p">)</span>
	<span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">K2</span>
        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="RK4"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK4">[docs]</a><span class="k">class</span> <span class="nc">RK4</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Standard RK4 method::</span>

<span class="sd">        u[n+1] = u[n] + (1/6.0)*(K1 + 2*K2 + 2*K3 + K4)</span>

<span class="sd">    where::</span>

<span class="sd">           K1 = dt*f(u[n], t[n])</span>
<span class="sd">           K2 = dt*f(u[n] + 0.5*K1, t[n] + 0.5*dt)</span>
<span class="sd">           K3 = dt*f(u[n] + 0.5*K2, t[n] + 0.5*dt)</span>
<span class="sd">           K4 = dt*f(u[n] + K3, t[n] + dt)</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 4th-order Runge-Kutta method&quot;</span>

<div class="viewcode-block" id="RK4.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK4.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">dt2</span> <span class="o">=</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.0</span>
        <span class="n">K1</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="n">K2</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">K1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt2</span><span class="p">)</span>
        <span class="n">K3</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">K2</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt2</span><span class="p">)</span>
        <span class="n">K4</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">K3</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="p">)</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">6.0</span><span class="p">)</span><span class="o">*</span><span class="p">(</span><span class="n">K1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">*</span><span class="n">K2</span> <span class="o">+</span> <span class="mi">2</span><span class="o">*</span><span class="n">K3</span> <span class="o">+</span> <span class="n">K4</span><span class="p">)</span>
        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="RK3"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK3">[docs]</a><span class="k">class</span> <span class="nc">RK3</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    RungeKutta3 method::</span>

<span class="sd">        u[n+1] = u[n] + (1/6.0)*(K1 + 4*K2 + K3)</span>

<span class="sd">    where::</span>

<span class="sd">        K1 = dt*f(u[n], t[n])</span>
<span class="sd">        K2 = dt*f(u[n] + 0.5*K1, t[n] + 0.5*dt)</span>
<span class="sd">        K3 = dt*f(u[n] - K1 + 2*K2, t[n] + dt)</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 3rd-order Runge-Kutta method&quot;</span>

<div class="viewcode-block" id="RK3.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK3.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">dt2</span> <span class="o">=</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.0</span>
        <span class="n">K1</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
        <span class="n">K2</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">K1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt2</span><span class="p">)</span>
        <span class="n">K3</span> <span class="o">=</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">-</span> <span class="n">K1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">*</span><span class="n">K2</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="p">)</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">6.0</span><span class="p">)</span><span class="o">*</span><span class="p">(</span><span class="n">K1</span> <span class="o">+</span> <span class="mi">4</span><span class="o">*</span><span class="n">K2</span> <span class="o">+</span> <span class="n">K3</span><span class="p">)</span>
        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="AdamsBashforth2"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth2">[docs]</a><span class="k">class</span> <span class="nc">AdamsBashforth2</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Second-order Adams-Bashforth method::</span>

<span class="sd">        u[n+1] = u[n] + dt/2.*(3*f(u[n], t[n]) - f(u[n-1], t[n-1]))</span>

<span class="sd">    for constant time step dt.</span>

<span class="sd">    RK2 is used as default solver in first step.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 2nd-order Adams-Bashforth method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;start_method&#39;</span><span class="p">,]</span>

<div class="viewcode-block" id="AdamsBashforth2.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth2.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># New solver instance for first steps</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">start_method</span><span class="p">)</span>
        <span class="c"># Create variables for holding f at previous time levels</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="bp">None</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="AdamsBashforth2.validate_data"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth2.validate_data">[docs]</a>    <span class="k">def</span> <span class="nf">validate_data</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;Check that the time steps are constant.&quot;&quot;&quot;</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">constant_time_step</span><span class="p">():</span>
            <span class="k">print</span> <span class="s">&#39;</span><span class="si">%s</span><span class="s"> must have constant time step&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__name__</span>
            <span class="k">return</span> <span class="bp">False</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="AdamsBashforth2.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth2.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">1</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>  <span class="c"># must be constant</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.</span><span class="o">*</span><span class="p">(</span><span class="mi">3</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">-</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">)</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="c"># User-specified method for the first step</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">time_points</span> <span class="o">=</span> <span class="p">[</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]]</span>
            <span class="n">u_starter</span><span class="p">,</span> <span class="n">t_starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u_starter</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>

        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="AdamsBashforth3"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth3">[docs]</a><span class="k">class</span> <span class="nc">AdamsBashforth3</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Third-order Adams-Bashforth method::</span>

<span class="sd">        u[n+1] = u[n] + dt/12.*(23*f(u[n], t[n]) - 16*f(u[n-1], t[n-1])</span>
<span class="sd">                                + 5*f(u[n-2], t[n-2]))</span>

<span class="sd">    for constant time step dt.</span>

<span class="sd">    RK2 is used as default solver for first steps.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 3rd-order Adams-Bashforth method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;start_method&#39;</span><span class="p">,]</span>

<div class="viewcode-block" id="AdamsBashforth3.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth3.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># New solver instance for first steps</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">start_method</span><span class="p">)</span>
        <span class="c"># Create variables for f at previous time levels</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="bp">None</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="bp">None</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="AdamsBashforth3.validate_data"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth3.validate_data">[docs]</a>    <span class="k">def</span> <span class="nf">validate_data</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">constant_time_step</span><span class="p">():</span>
            <span class="k">print</span> <span class="s">&#39;</span><span class="si">%s</span><span class="s"> must have constant time step&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__name__</span>
            <span class="k">return</span> <span class="bp">False</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="AdamsBashforth3.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth3.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">2</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>  <span class="c"># must be constant</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">12.</span><span class="o">*</span><span class="p">(</span><span class="mi">23</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">-</span> <span class="mi">16</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">+</span> <span class="mi">5</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">)</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span>

        <span class="k">else</span><span class="p">:</span>
            <span class="c"># Start method</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">time_points</span> <span class="o">=</span> <span class="p">[</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]]</span>
            <span class="n">u_starter</span><span class="p">,</span> <span class="n">t_starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u_starter</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
            <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="AdamsBashMoulton2"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton2">[docs]</a><span class="k">class</span> <span class="nc">AdamsBashMoulton2</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Two-step (3rd-order) Adams-Bashforth method::</span>

<span class="sd">        predictor = u[n] + dt/12.*(23.*f(u[n], t[n]) - 16*f(u[n-1], t[n-1]) +</span>
<span class="sd">                            5*f(u[n-2], t[n-2]))</span>
<span class="sd">        corrector = u[n] + dt/12.*(8.*f(u[n], t[n]) - f(u[n-1], t[n-1]) +</span>
<span class="sd">                            5*f(predictor, t[n+1]))</span>

<span class="sd">    for constant time step dt.</span>

<span class="sd">    RK2 is used as default solver for first steps.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 2nd-order Adams-Bashforth-Moulton method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;start_method&#39;</span><span class="p">,]</span>

<div class="viewcode-block" id="AdamsBashMoulton2.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton2.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># New solver instance for first steps</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">start_method</span><span class="p">)</span>
        <span class="c"># Create variables for f at previous time levels</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="bp">None</span><span class="p">,</span> <span class="bp">None</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="AdamsBashMoulton2.validate_data"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton2.validate_data">[docs]</a>    <span class="k">def</span> <span class="nf">validate_data</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">constant_time_step</span><span class="p">():</span>
            <span class="k">print</span> <span class="s">&#39;</span><span class="si">%s</span><span class="s"> must have constant time step&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__name__</span>
            <span class="k">return</span> <span class="bp">False</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="AdamsBashMoulton2.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton2.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">2</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>  <span class="c"># must be constant</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">predictor</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">12.</span><span class="o">*</span><span class="p">(</span><span class="mf">23.</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">-</span> <span class="mi">16</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">+</span> \
                                  <span class="mi">5</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">12.</span><span class="o">*</span><span class="p">(</span><span class="mi">8</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">-</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">+</span> \
                                  <span class="mi">5</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">predictor</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span> <span class="o">+</span> <span class="mi">1</span><span class="p">]))</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="c"># Start method</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">time_points</span> <span class="o">=</span> <span class="p">[</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]]</span>
            <span class="n">u_starter</span><span class="p">,</span> <span class="n">t_starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u_starter</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
            <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>

        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="AdamsBashforth4"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth4">[docs]</a><span class="k">class</span> <span class="nc">AdamsBashforth4</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Fourth-order Adams-Bashforth method::</span>

<span class="sd">        u[n+1] = u[n] + dt/24.*(55.*f(u[n], t[n]) - 59*f(u[n-1], t[n-1]) +</span>
<span class="sd">                                37*f(u[n-2], t[n-2]) - 9*f(u[n-3], t[n-3]))</span>

<span class="sd">    for constant time step dt.</span>

<span class="sd">    RK2 is used as default solver for first steps.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 4th-order Adams-Bashforth method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;start_method&#39;</span><span class="p">,]</span>

<div class="viewcode-block" id="AdamsBashforth4.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth4.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># New solver instance for first steps</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">start_method</span><span class="p">)</span>
        <span class="c"># Create variables for f at previous time levels</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span> <span class="o">=</span> <span class="bp">None</span><span class="p">,</span> <span class="bp">None</span><span class="p">,</span> <span class="bp">None</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="AdamsBashforth4.validate_data"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth4.validate_data">[docs]</a>    <span class="k">def</span> <span class="nf">validate_data</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">constant_time_step</span><span class="p">():</span>
            <span class="k">print</span> <span class="s">&#39;</span><span class="si">%s</span><span class="s"> must have constant time step&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__name__</span>
            <span class="k">return</span> <span class="bp">False</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="AdamsBashforth4.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashforth4.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">3</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>  <span class="c"># must be constant</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">24.</span><span class="o">*</span><span class="p">(</span><span class="mf">55.</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">-</span> <span class="mi">59</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">+</span> \
                                  <span class="mi">37</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">-</span> <span class="mi">9</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span><span class="p">)</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span> <span class="o">=</span> \
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="c"># Start method</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">time_points</span> <span class="o">=</span> <span class="p">[</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]]</span>
            <span class="n">u_starter</span><span class="p">,</span> <span class="n">t_starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u_starter</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
            <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>
            <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">2</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">2</span><span class="p">])</span>

        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="AdamsBashMoulton3"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton3">[docs]</a><span class="k">class</span> <span class="nc">AdamsBashMoulton3</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Three-step (4th-order) Adams-Bashforth method::</span>

<span class="sd">        predictor = u[n] + dt/24.*(55.*f(u[n], t[n]) - 59*f(u[n-1], t[n-1]) +</span>
<span class="sd">                                   37*f(u[n-2], t[n-2]) - 9*f(u[n-3], t[n-3]))</span>
<span class="sd">        corrector = u[n] + dt/24.*(19.*f(u[n], t[n]) - 5*f(u[n-1], t[n-1]) +</span>
<span class="sd">                                   f(u[n-2], t[n-2]) + 9*f(predictor, t[n+1]))</span>

<span class="sd">    for constant time step dt.</span>

<span class="sd">    RK2 is used as default solver for first steps.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 3rd-order Adams-Bashforth-Moulton method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;start_method&#39;</span><span class="p">,]</span>

<div class="viewcode-block" id="AdamsBashMoulton3.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton3.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># New solver instance for first steps</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">start_method</span><span class="p">)</span>
        <span class="c"># Create variables for f at previous time levels</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span> <span class="o">=</span> <span class="bp">None</span><span class="p">,</span> <span class="bp">None</span><span class="p">,</span> <span class="bp">None</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="AdamsBashMoulton3.validate_data"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton3.validate_data">[docs]</a>    <span class="k">def</span> <span class="nf">validate_data</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">constant_time_step</span><span class="p">():</span>
            <span class="k">print</span> <span class="s">&#39;</span><span class="si">%s</span><span class="s"> must have constant time step&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__name__</span>
            <span class="k">return</span> <span class="bp">False</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="bp">True</span>
</div>
<div class="viewcode-block" id="AdamsBashMoulton3.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdamsBashMoulton3.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

        <span class="k">if</span> <span class="n">n</span> <span class="o">&gt;=</span> <span class="mi">3</span><span class="p">:</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>  <span class="c"># must be constant</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">predictor</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">24.</span><span class="o">*</span><span class="p">(</span><span class="mf">55.</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">-</span> <span class="mi">59</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">+</span> \
                                  <span class="mi">37</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">-</span> <span class="mi">9</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">24.</span><span class="o">*</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">-</span> <span class="mi">5</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">+</span> <span class="mi">19</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_n</span> <span class="o">+</span> \
                                  <span class="mi">9</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">predictor</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span> <span class="o">+</span> <span class="mi">1</span><span class="p">]))</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span> <span class="o">=</span> \
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="c"># Start method</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
            <span class="n">time_points</span> <span class="o">=</span> <span class="p">[</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]]</span>
            <span class="n">u_starter</span><span class="p">,</span> <span class="n">t_starter</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">starter</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u_starter</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_3</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
            <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_2</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>
            <span class="k">elif</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">2</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">f_n_1</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="mi">2</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="mi">2</span><span class="p">])</span>

        <span class="k">return</span> <span class="n">u_new</span>


</div></div>
<div class="viewcode-block" id="MidpointIter"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MidpointIter">[docs]</a><span class="k">class</span> <span class="nc">MidpointIter</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    A midpoint/central difference method with max_iter fixed-point</span>
<span class="sd">    iterations to solve the nonlinear system.</span>
<span class="sd">    The Forward Euler scheme is recovered if max_iter=1 and f(u,t)</span>
<span class="sd">    is independent of t. For max_iter=2 we have the Heun/RK2 scheme.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Explicit 2nd-order iterated Midpoint method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
                           <span class="p">[</span><span class="s">&#39;max_iter&#39;</span><span class="p">,</span> <span class="s">&#39;eps_iter&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="MidpointIter.adjust_parameters"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MidpointIter.adjust_parameters">[docs]</a>    <span class="k">def</span> <span class="nf">adjust_parameters</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span><span class="p">[</span><span class="s">&#39;max_iter&#39;</span><span class="p">][</span><span class="s">&#39;default&#39;</span><span class="p">]</span> <span class="o">=</span> <span class="mi">3</span>
</div>
<div class="viewcode-block" id="MidpointIter.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MidpointIter.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;v&#39;</span><span class="p">):</span>  <span class="c"># v is a help array needed in the method</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
                <span class="c"># Scalar ODE: v can be one-dim array</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">v</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">zeros</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">max_iter</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">dtype</span><span class="p">)</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="c"># System of ODEs: v must be two-dim array</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">v</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">zeros</span><span class="p">((</span><span class="bp">self</span><span class="o">.</span><span class="n">max_iter</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">),</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">dtype</span><span class="p">)</span>

        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">v</span> <span class="o">=</span> \
           <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">v</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>

        <span class="n">v</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">q</span> <span class="o">=</span> <span class="mi">0</span>
        <span class="n">v_finished</span> <span class="o">=</span> <span class="bp">False</span>   <span class="c"># |v[q]-v[q-1]| &lt; eps</span>
        <span class="k">while</span> <span class="ow">not</span> <span class="n">v_finished</span> <span class="ow">and</span> <span class="n">q</span> <span class="o">&lt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">max_iter</span><span class="p">:</span>
            <span class="n">q</span> <span class="o">+=</span> <span class="mi">1</span>
            <span class="n">v</span><span class="p">[</span><span class="n">q</span><span class="p">]</span> <span class="o">=</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="mf">0.5</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">v</span><span class="p">[</span><span class="n">q</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span> <span class="o">+</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]))</span>
            <span class="k">if</span> <span class="nb">abs</span><span class="p">(</span><span class="n">v</span><span class="p">[</span><span class="n">q</span><span class="p">]</span> <span class="o">-</span> <span class="n">v</span><span class="p">[</span><span class="n">q</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span><span class="o">.</span><span class="n">max</span><span class="p">()</span> <span class="o">&lt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">eps_iter</span><span class="p">:</span>
                <span class="n">v_finished</span> <span class="o">=</span> <span class="bp">True</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">num_iterations</span> <span class="o">=</span> <span class="n">q</span>

        <span class="n">u_new</span> <span class="o">=</span> <span class="n">v</span><span class="p">[</span><span class="n">q</span><span class="p">]</span>
        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="approximate_Jacobian"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.approximate_Jacobian">[docs]</a><span class="k">def</span> <span class="nf">approximate_Jacobian</span><span class="p">(</span><span class="n">f</span><span class="p">,</span> <span class="n">u0</span><span class="p">,</span> <span class="n">t0</span><span class="p">,</span> <span class="n">h</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Compute approximate Jacobian of fucntion f at current point (u0,t0).</span>
<span class="sd">    Method: forward finite difference approximation with step</span>
<span class="sd">    size h.</span>
<span class="sd">    Output: a two-dimensional array holding the Jacobian matrix.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">u0</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">u0</span><span class="p">)</span>
    <span class="n">f0</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">u0</span><span class="p">,</span> <span class="n">t0</span><span class="p">))</span>
    <span class="n">neq</span> <span class="o">=</span> <span class="nb">len</span><span class="p">(</span><span class="n">u0</span><span class="p">)</span>
    <span class="n">J</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">zeros</span><span class="p">((</span><span class="n">neq</span><span class="p">,</span> <span class="n">neq</span><span class="p">),</span> <span class="nb">float</span><span class="p">)</span>
    <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="n">neq</span><span class="p">):</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="n">u0</span><span class="o">.</span><span class="n">copy</span><span class="p">()</span>
        <span class="n">u_new</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">+=</span> <span class="n">h</span>
        <span class="n">J</span><span class="p">[</span><span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="p">(</span><span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">f</span><span class="p">(</span><span class="n">u_new</span><span class="p">,</span> <span class="n">t0</span><span class="p">))</span> <span class="o">-</span> <span class="n">f0</span><span class="p">)</span><span class="o">/</span><span class="n">h</span>
    <span class="k">return</span> <span class="n">J</span><span class="o">.</span><span class="n">transpose</span><span class="p">()</span>

</div>
<div class="viewcode-block" id="odefun_sympy"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odefun_sympy">[docs]</a><span class="k">class</span> <span class="nc">odefun_sympy</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Wrapper for the sympy.mpmath.odefun method, which applies a high-order</span>
<span class="sd">    Taylor series method to solve ODEs.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Very accurate high order Taylor method (from SymPy)&quot;</span>

<div class="viewcode-block" id="odefun_sympy.initialize"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odefun_sympy.initialize">[docs]</a>    <span class="k">def</span> <span class="nf">initialize</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">try</span><span class="p">:</span>
            <span class="kn">import</span> <span class="nn">sympy</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">sympy</span> <span class="o">=</span> <span class="n">sympy</span>
        <span class="k">except</span> <span class="ne">ImportError</span><span class="p">:</span>
            <span class="k">raise</span> <span class="ne">ImportError</span><span class="p">,</span><span class="s">&#39;sympy is not installed - needed for sympy_odefun&#39;</span>
</div>
<div class="viewcode-block" id="odefun_sympy.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odefun_sympy.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># sympy.odefun requires f(t, u), not f(u, t, *args, **kwargs)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f4odefun</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">t</span><span class="p">,</span> <span class="n">u</span><span class="p">:</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_args</span><span class="p">,</span> <span class="o">**</span><span class="bp">self</span><span class="o">.</span><span class="n">f_kwargs</span><span class="p">)</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="odefun_sympy.solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odefun_sympy.solve">[docs]</a>    <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">time_points</span><span class="p">,</span> <span class="n">terminate</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        The complete solve method must be overridded in this class</span>
<span class="sd">        since sympy.mpmath.odefun is such a solve method.</span>

<span class="sd">        The class stores an attribute ufunc (return from odefun)</span>
<span class="sd">        which can be used to evaluate u at any time point (ufunc(t)).</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="c"># Note: disk_storage is ignored - all computations in odefun</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">()</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">sympy</span><span class="o">.</span><span class="n">mpmath</span><span class="o">.</span><span class="n">mp</span><span class="o">.</span><span class="n">dps</span> <span class="o">=</span> <span class="mi">15</span>  <span class="c"># accuracy</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">ufunc</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">sympy</span><span class="o">.</span><span class="n">mpmath</span><span class="o">.</span><span class="n">odefun</span><span class="p">(</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f4odefun</span><span class="p">,</span> <span class="n">time_points</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">)</span>

        <span class="c"># u and t to be returned are now computed by sampling self.ufunc</span>
        <span class="c"># at the specified time points</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">array</span><span class="p">([</span><span class="bp">self</span><span class="o">.</span><span class="n">ufunc</span><span class="p">(</span><span class="n">t</span><span class="p">)</span> <span class="k">for</span> <span class="n">t</span> <span class="ow">in</span> <span class="n">time_points</span><span class="p">])</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>

        <span class="k">if</span> <span class="n">terminate</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span>
            <span class="k">for</span> <span class="n">step_no</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)):</span>
                <span class="k">if</span> <span class="n">terminate</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="n">step_no</span><span class="p">):</span>
                    <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[:</span><span class="n">step_no</span><span class="o">+</span><span class="mi">1</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[:</span><span class="n">step_no</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>


</div></div>
<div class="viewcode-block" id="SolverImplicit"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.SolverImplicit">[docs]</a><span class="k">class</span> <span class="nc">SolverImplicit</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Super class for implicit methods for ODEs.</span>
<span class="sd">    Existing solvers are: BackwardEuler, Backward2Step, ThetaRule</span>
<span class="sd">    &quot;&quot;&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="s">&#39;jac_args&#39;</span><span class="p">,</span> <span class="s">&#39;jac_kwargs&#39;</span><span class="p">,</span> <span class="s">&#39;h_in_fd_jac&#39;</span><span class="p">,</span>
         <span class="s">&#39;nonlinear_solver&#39;</span><span class="p">,</span> <span class="s">&#39;max_iter&#39;</span><span class="p">,</span> <span class="s">&#39;eps_iter&#39;</span><span class="p">,</span> <span class="s">&#39;relaxation&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="SolverImplicit.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.SolverImplicit.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># Set appropriate value of nonlinear_solver if undefined</span>
        <span class="k">if</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="bp">None</span><span class="p">)</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>   <span class="c"># no jac provided</span>
            <span class="k">if</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;nonlinear_solver&#39;</span><span class="p">,</span> <span class="bp">None</span><span class="p">)</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">nonlinear_solver</span> <span class="o">=</span> <span class="s">&#39;Picard&#39;</span>  <span class="c"># default if no jac provided</span>
            <span class="k">elif</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;nonlinear_solver&#39;</span><span class="p">)</span> <span class="o">==</span> <span class="s">&#39;Newton&#39;</span><span class="p">:</span>
                 <span class="c"># Approximate jacobian with finite difference approx</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span> <span class="o">=</span> <span class="n">approximate_Jacobian</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">jac</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">:</span> \
                    <span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">h_in_fd_jac</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">if</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;nonlinear_solver&#39;</span><span class="p">,</span> <span class="bp">None</span><span class="p">)</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">nonlinear_solver</span> <span class="o">=</span> <span class="s">&#39;Newton&#39;</span>  <span class="c"># default if jac provided</span>
            <span class="c"># Wrap user-supplied Jacobian in the way f is wrapped</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">users_jac</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">jac</span>  <span class="c"># save</span>
            <span class="n">jac</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">jac</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">jac</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">:</span> \
                <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">jac</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac_args</span><span class="p">,</span> <span class="o">**</span><span class="bp">self</span><span class="o">.</span><span class="n">jac_kwargs</span><span class="p">))</span>

        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="SolverImplicit.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.SolverImplicit.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">n</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span>
        <span class="n">un</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">t_new</span><span class="p">,</span> <span class="n">tn</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t_new</span> <span class="o">-</span> <span class="n">tn</span>

        <span class="c"># General solver routine with Newton or Picard</span>
        <span class="c"># Newton with Finite-Differential or exact Jac</span>
        <span class="n">i</span><span class="p">,</span> <span class="n">error</span> <span class="o">=</span> <span class="mi">1</span><span class="p">,</span> <span class="mf">1E+30</span>
        <span class="c"># Forward Euler step for initial guess for nonlinear solver</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="n">un</span> <span class="o">+</span> <span class="p">(</span><span class="n">t_new</span><span class="o">-</span><span class="n">tn</span><span class="p">)</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">un</span><span class="p">,</span><span class="n">tn</span><span class="p">)</span>
        <span class="c"># control by number of intern steps and error tolerance</span>
        <span class="k">while</span> <span class="n">i</span> <span class="o">&lt;=</span> <span class="bp">self</span><span class="o">.</span><span class="n">max_iter</span> <span class="ow">and</span> <span class="n">error</span> <span class="o">&gt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">eps_iter</span><span class="p">:</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">nonlinear_solver</span> <span class="o">==</span> <span class="s">&#39;Picard&#39;</span><span class="p">:</span>
                <span class="n">u_new</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">Picard_update</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span>
            <span class="k">elif</span> <span class="bp">self</span><span class="o">.</span><span class="n">nonlinear_solver</span> <span class="o">==</span> <span class="s">&#39;Newton&#39;</span><span class="p">:</span>
                <span class="n">F</span><span class="p">,</span> <span class="n">Jac</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">Newton_system</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span>
                <span class="n">du</span> <span class="o">=</span> <span class="n">F</span><span class="o">/</span><span class="n">Jac</span> <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">==</span> <span class="mi">1</span> <span class="k">else</span> <span class="n">np</span><span class="o">.</span><span class="n">linalg</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">Jac</span><span class="p">,</span> <span class="n">F</span><span class="p">)</span>
                <span class="n">u_new</span> <span class="o">=</span> <span class="n">u_new</span> <span class="o">-</span> <span class="n">du</span>
            <span class="k">elif</span> <span class="bp">self</span><span class="o">.</span><span class="n">nonlinear_solver</span> <span class="o">==</span> <span class="s">&#39;FixedPoint&#39;</span><span class="p">:</span>
                <span class="n">u_new</span> <span class="o">=</span> <span class="n">un</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u_new</span><span class="p">,</span><span class="n">tn</span><span class="p">)</span>
            <span class="n">error</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">abs</span><span class="p">(</span><span class="n">u_new</span> <span class="o">-</span> <span class="n">u_new</span><span class="p">)</span><span class="o">.</span><span class="n">max</span><span class="p">()</span>
            <span class="n">r</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">relaxation</span>    <span class="c"># Relax factor</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">r</span><span class="o">*</span><span class="n">u_new</span> <span class="o">+</span> <span class="p">(</span><span class="mi">1</span><span class="o">-</span><span class="n">r</span><span class="p">)</span><span class="o">*</span><span class="n">un</span>
            <span class="n">i</span> <span class="o">+=</span> <span class="mi">1</span>
        <span class="k">return</span> <span class="n">u_new</span>
</div></div>
<div class="viewcode-block" id="BackwardEuler"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.BackwardEuler">[docs]</a><span class="k">class</span> <span class="nc">BackwardEuler</span><span class="p">(</span><span class="n">SolverImplicit</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Implicit Backward Euler method::</span>

<span class="sd">       u[n+1] = u[n] + dt*f(t[n+1], u[n+1])</span>

<span class="sd">    The nonlinear system is solved by Newton or Picard iteration.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Implicit 1st-order Backward Euler method&quot;</span>

<div class="viewcode-block" id="BackwardEuler.Picard_update"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.BackwardEuler.Picard_update">[docs]</a>    <span class="k">def</span> <span class="nf">Picard_update</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="k">return</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
</div>
<div class="viewcode-block" id="BackwardEuler.Newton_system"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.BackwardEuler.Newton_system">[docs]</a>    <span class="k">def</span> <span class="nf">Newton_system</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">F</span> <span class="o">=</span> <span class="n">ukp1</span> <span class="o">-</span> <span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]))</span>
        <span class="n">J</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">eye</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">)</span> <span class="o">-</span> <span class="n">dt</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">F</span><span class="p">,</span> <span class="n">J</span>

</div></div>
<div class="viewcode-block" id="Backward2Step"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Backward2Step">[docs]</a><span class="k">class</span> <span class="nc">Backward2Step</span><span class="p">(</span><span class="n">SolverImplicit</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Implicit Backward Euler method with 2 steps::</span>

<span class="sd">         u[n+1] = u[n]*4/3 - u[n-1]/3 + (t[n+1-t[n-1]])*f(t[n+1], u[n+1])/3</span>

<span class="sd">    The 1st-order Backward Euler method is used for the first step.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Implicit 2nd-order Backward Euler method&quot;</span>

<div class="viewcode-block" id="Backward2Step.Picard_update"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Backward2Step.Picard_update">[docs]</a>    <span class="k">def</span> <span class="nf">Picard_update</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
            <span class="c"># Backward Euler as starter</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
            <span class="k">return</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="n">dt2</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="k">return</span> <span class="mf">4.</span><span class="o">/</span><span class="mi">3</span><span class="o">*</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">-</span> <span class="mf">1.</span><span class="o">/</span><span class="mi">3</span><span class="o">*</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="p">(</span><span class="mf">1.</span><span class="o">/</span><span class="mi">3</span><span class="p">)</span><span class="o">*</span><span class="n">dt2</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
</div>
<div class="viewcode-block" id="Backward2Step.Newton_system"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Backward2Step.Newton_system">[docs]</a>    <span class="k">def</span> <span class="nf">Newton_system</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="k">if</span> <span class="n">n</span> <span class="o">==</span> <span class="mi">0</span><span class="p">:</span>
            <span class="c"># Backward Euler as starter</span>
            <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
            <span class="n">F</span> <span class="o">=</span> <span class="n">ukp1</span> <span class="o">-</span> <span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]))</span>
            <span class="n">J</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">eye</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">)</span> <span class="o">-</span> <span class="n">dt</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="n">dt2</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
            <span class="n">F</span> <span class="o">=</span> <span class="n">ukp1</span> <span class="o">-</span> <span class="p">(</span><span class="mf">4.</span><span class="o">/</span><span class="mi">3</span><span class="o">*</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">-</span> <span class="mf">1.</span><span class="o">/</span><span class="mi">3</span><span class="o">*</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span> <span class="o">+</span> <span class="p">(</span><span class="mf">1.</span><span class="o">/</span><span class="mi">3</span><span class="p">)</span><span class="o">*</span><span class="n">dt2</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]))</span>
            <span class="n">J</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">eye</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">)</span> <span class="o">-</span> <span class="p">(</span><span class="mf">1.</span><span class="o">/</span><span class="mi">3</span><span class="p">)</span><span class="o">*</span><span class="n">dt2</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">F</span><span class="p">,</span> <span class="n">J</span>

</div></div>
<div class="viewcode-block" id="ThetaRule"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ThetaRule">[docs]</a><span class="k">class</span> <span class="nc">ThetaRule</span><span class="p">(</span><span class="n">SolverImplicit</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    This class implements the implicit theta-rule method for solving</span>
<span class="sd">    ODEs. The method includes a parameter theta used to weight the</span>
<span class="sd">    previous and new time step when evaluating the right-hand side::</span>

<span class="sd">       u[n+1] = u[n] + dt*(theta*f(u[n+1],t[n+1]) + (1 - theta)*f(u[n],t[n]))</span>

<span class="sd">    Here, ``theta`` is a float in [0,1].</span>

<span class="sd">    The nonlinear system is solved by Picard or Newton iteration.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Unified Forward/Backward Euler and Midpoint methods&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">SolverImplicit</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> <span class="p">[</span><span class="s">&#39;theta&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="ThetaRule.Picard_update"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ThetaRule.Picard_update">[docs]</a>    <span class="k">def</span> <span class="nf">Picard_update</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">theta</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">theta</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="k">return</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">theta</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span> <span class="o">+</span> <span class="p">(</span><span class="mi">1</span><span class="o">-</span><span class="n">theta</span><span class="p">)</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">])</span>
</div>
<div class="viewcode-block" id="ThetaRule.Newton_system"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ThetaRule.Newton_system">[docs]</a>    <span class="k">def</span> <span class="nf">Newton_system</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">theta</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">theta</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">F</span> <span class="o">=</span> <span class="n">ukp1</span> <span class="o">-</span> <span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">theta</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span> <span class="o">+</span> <span class="p">(</span><span class="mi">1</span><span class="o">-</span><span class="n">theta</span><span class="p">)</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]))</span>
        <span class="n">J</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">eye</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">)</span> <span class="o">-</span> <span class="n">theta</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">F</span><span class="p">,</span> <span class="n">J</span>

</div></div>
<div class="viewcode-block" id="MidpointImplicit"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MidpointImplicit">[docs]</a><span class="k">class</span> <span class="nc">MidpointImplicit</span><span class="p">(</span><span class="n">SolverImplicit</span><span class="p">):</span>
    <span class="sd">&#39;&#39;&#39;</span>
<span class="sd">    Midpoint Implicit method::</span>

<span class="sd">       u[n+1] = u[n] + dt*f((u[n+1] + u[n])/2., t[n] + dt/2.)</span>

<span class="sd">    The nonlinear system is solved by Picard or Newton iteration.</span>
<span class="sd">    &#39;&#39;&#39;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Implicit 2nd-order Midpoint method&quot;</span>

<div class="viewcode-block" id="MidpointImplicit.Picard_update"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MidpointImplicit.Picard_update">[docs]</a>    <span class="k">def</span> <span class="nf">Picard_update</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="k">return</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">((</span><span class="n">ukp1</span> <span class="o">+</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span><span class="o">/</span><span class="mf">2.</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="MidpointImplicit.Newton_system"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.MidpointImplicit.Newton_system">[docs]</a>    <span class="k">def</span> <span class="nf">Newton_system</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">ukp1</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span>
        <span class="n">F</span> <span class="o">=</span> <span class="n">ukp1</span> <span class="o">-</span>  <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">f</span><span class="p">((</span><span class="n">ukp1</span> <span class="o">+</span> <span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">])</span><span class="o">/</span><span class="mf">2.</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">]</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.</span><span class="p">)</span>
        <span class="n">J</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">eye</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">)</span> <span class="o">-</span> <span class="n">dt</span><span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">(</span><span class="n">ukp1</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">return</span> <span class="n">F</span><span class="p">,</span> <span class="n">J</span>


</div></div>
<div class="viewcode-block" id="Adaptive"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Adaptive">[docs]</a><span class="k">class</span> <span class="nc">Adaptive</span><span class="p">(</span><span class="n">Solver</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;Superclass for adaptive solvers.&quot;&quot;&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Solver</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;rtol&#39;</span><span class="p">,</span> <span class="s">&#39;atol&#39;</span><span class="p">,</span> <span class="s">&#39;first_step&#39;</span><span class="p">,</span> <span class="s">&#39;min_step&#39;</span><span class="p">,</span> <span class="s">&#39;max_step&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="Adaptive.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Adaptive.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># Let first_step, min_step and max_ste, if not given, be</span>
        <span class="c"># computed from the user&#39;s time points, available as self.t.</span>

        <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;first_step&#39;</span><span class="p">):</span>
            <span class="c"># Use user&#39;s first step</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">set</span><span class="p">(</span><span class="n">first_step</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
        <span class="n">time_steps</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">:]</span> <span class="o">-</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[:</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;min_step&#39;</span><span class="p">):</span>
            <span class="c"># Use 1/100 of the user&#39;s smallest step</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">set</span><span class="p">(</span><span class="n">min_step</span><span class="o">=</span><span class="mf">0.01</span><span class="o">*</span><span class="n">time_steps</span><span class="o">.</span><span class="n">min</span><span class="p">())</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;max_step&#39;</span><span class="p">):</span>
            <span class="c"># Use 10 times the user&#39;s greatest step</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">set</span><span class="p">(</span><span class="n">max_step</span><span class="o">=</span><span class="mi">10</span><span class="o">*</span><span class="n">time_steps</span><span class="o">.</span><span class="n">max</span><span class="p">())</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>

        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">u_all</span> <span class="o">=</span> <span class="p">[</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">]]</span>  <span class="c"># corresponding u values</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t_all</span> <span class="o">=</span> <span class="p">[</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">]]</span>      <span class="c"># computed time levels</span>

</div>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    # Better to have self.has_ut_all to decide if self.u_all and self.t_all</span>
<span class="sd">    # are computed</span>
<span class="sd">    def solve(self, time_points, terminate=None):</span>
<span class="sd">        # Check that self.u_all and self.t_all are ok</span>
<span class="sd">        u, t = Solver.solve(self, time_points, terminate)</span>
<span class="sd">        if len(self.u_all) == 1:</span>
<span class="sd">            # self.u_all was not computed</span>
<span class="sd">            self.u_all = self.u</span>
<span class="sd">            self.t_all = self.t</span>
<span class="sd">        else:</span>
<span class="sd">            self.u_all, self.t_all = np.array(self.u_all), np.array(self.t_all)</span>
<span class="sd">        return u, t</span>
<span class="sd">    &quot;&quot;&quot;</span>
</div>
<div class="viewcode-block" id="AdaptiveResidual"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdaptiveResidual">[docs]</a><span class="k">class</span> <span class="nc">AdaptiveResidual</span><span class="p">(</span><span class="n">Adaptive</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Designed for educational purposes to demonstrate a possible</span>
<span class="sd">    adaptive strategy.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Very simple adaptive strategy based on the residual&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Adaptive</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
                           <span class="p">[</span><span class="s">&#39;solver&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="AdaptiveResidual.__init__"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdaptiveResidual.__init__">[docs]</a>    <span class="k">def</span> <span class="nf">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="n">Adaptive</span><span class="o">.</span><span class="n">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">)</span>
        <span class="k">if</span> <span class="s">&#39;solver&#39;</span> <span class="ow">in</span> <span class="n">kwargs</span><span class="p">:</span>
            <span class="k">del</span> <span class="n">kwargs</span><span class="p">[</span><span class="s">&#39;solver&#39;</span><span class="p">]</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">solver</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">switch_to</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="AdaptiveResidual.residual"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdaptiveResidual.residual">[docs]</a>    <span class="k">def</span> <span class="nf">residual</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">u_n</span><span class="p">,</span> <span class="n">u_next</span><span class="p">,</span> <span class="n">t_n</span><span class="p">,</span> <span class="n">t_next</span><span class="p">):</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t_next</span> <span class="o">-</span> <span class="n">t_n</span>
        <span class="n">t_mean</span> <span class="o">=</span> <span class="mf">0.5</span><span class="o">*</span><span class="p">(</span><span class="n">t_n</span> <span class="o">+</span> <span class="n">t_next</span><span class="p">)</span>
        <span class="n">u_mean</span> <span class="o">=</span> <span class="mf">0.5</span><span class="o">*</span><span class="p">(</span><span class="n">u_n</span> <span class="o">+</span> <span class="n">u_next</span><span class="p">)</span>
        <span class="n">u_diff</span> <span class="o">=</span> <span class="n">u_next</span> <span class="o">-</span> <span class="n">u_n</span>
        <span class="c"># Central 2nd order difference approx to the residual</span>
        <span class="n">r</span> <span class="o">=</span> <span class="n">u_diff</span><span class="o">/</span><span class="n">dt</span> <span class="o">-</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">(</span><span class="n">u_mean</span><span class="p">,</span> <span class="n">t_mean</span><span class="p">)</span>
        <span class="n">r</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">abs</span><span class="p">(</span><span class="n">r</span><span class="p">)</span><span class="o">.</span><span class="n">max</span><span class="p">()</span>
        <span class="k">return</span> <span class="n">r</span>
</div>
<div class="viewcode-block" id="AdaptiveResidual.solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.AdaptiveResidual.solve">[docs]</a>    <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">time_points</span><span class="p">,</span> <span class="n">terminate</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span>
        <span class="k">if</span> <span class="n">terminate</span> <span class="ow">is</span> <span class="bp">None</span><span class="p">:</span>
            <span class="n">terminate</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">n</span><span class="p">:</span> <span class="bp">False</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">users_time_points</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span><span class="o">.</span><span class="n">copy</span><span class="p">()</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">users_time_points</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">()</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">validate_data</span><span class="p">()</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="p">[</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">]</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="p">[</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">]]</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">)</span>
        <span class="k">for</span> <span class="n">k</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="mi">1</span><span class="p">,</span><span class="nb">len</span><span class="p">(</span><span class="n">t</span><span class="p">)):</span>
            <span class="n">R</span> <span class="o">=</span> <span class="mf">1E+20</span>
            <span class="c"># Try to jump until next user point in time</span>
            <span class="n">ntpoints</span> <span class="o">=</span> <span class="mi">1</span>
            <span class="c"># Halve the time step until residual is small enough</span>
            <span class="k">while</span> <span class="n">R</span> <span class="o">&gt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">atol</span><span class="p">:</span>
                <span class="n">time_points</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">linspace</span><span class="p">(</span><span class="n">t</span><span class="p">[</span><span class="n">k</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">k</span><span class="p">],</span> <span class="n">ntpoints</span><span class="o">+</span><span class="mi">1</span><span class="p">)</span>
                <span class="n">dt</span> <span class="o">=</span> <span class="n">time_points</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="n">time_points</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span>
                <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&#39;dt=</span><span class="si">%g</span><span class="s">, &#39;</span> <span class="o">%</span> <span class="n">dt</span><span class="p">,</span>
                <span class="k">if</span> <span class="n">dt</span> <span class="o">&lt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">min_step</span> <span class="ow">and</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&#39;too small </span><span class="si">%s</span><span class="s"> &lt; </span><span class="si">%s</span><span class="s">, &#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">dt</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">min_step</span><span class="p">)</span>
                    <span class="k">print</span>
                    <span class="k">break</span>
                <span class="k">if</span> <span class="n">dt</span> <span class="o">&gt;</span> <span class="bp">self</span><span class="o">.</span><span class="n">max_step</span> <span class="ow">and</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&#39;too large </span><span class="si">%s</span><span class="s"> &gt; </span><span class="si">%s</span><span class="s">, &#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">dt</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">max_step</span><span class="p">)</span>
                    <span class="k">break</span>

                <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">set_initial_condition</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span>
                <span class="n">u_new</span><span class="p">,</span> <span class="n">t_new</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">solve</span><span class="p">(</span><span class="n">time_points</span><span class="p">,</span> <span class="n">terminate</span><span class="o">=</span><span class="bp">None</span><span class="p">)</span>
                <span class="c">#R = self.residual(u_new[-2], u_new[-1], t_new[-2], t_new[-1])</span>
                <span class="n">R</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">residual</span><span class="p">(</span><span class="n">u_new</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">u_new</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span> <span class="n">t_new</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t_new</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span>
                <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span> <span class="o">&gt;</span> <span class="mi">0</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&#39;</span><span class="se">\n</span><span class="si">%d</span><span class="s"> time points in (t[</span><span class="si">%d</span><span class="s">], t[</span><span class="si">%d</span><span class="s">]) = (</span><span class="si">%.3g</span><span class="s">, </span><span class="si">%.3g</span><span class="s">), &#39;</span> \
                        <span class="o">%</span> <span class="p">(</span><span class="n">ntpoints</span><span class="o">+</span><span class="mi">1</span><span class="p">,</span> <span class="n">k</span><span class="o">-</span><span class="mi">1</span><span class="p">,</span> <span class="n">k</span><span class="p">,</span> <span class="n">t</span><span class="p">[</span><span class="n">k</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span> <span class="n">t</span><span class="p">[</span><span class="n">k</span><span class="p">])</span>
                    <span class="k">print</span> <span class="s">&#39;Residual=</span><span class="si">%.1E</span><span class="s">, tolerance=</span><span class="si">%.1E</span><span class="s">, calling </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                        <span class="p">(</span><span class="n">R</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">atol</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>
                <span class="c"># reintegrate with time_step = dt/2</span>
                <span class="n">ntpoints</span> <span class="o">*=</span> <span class="mi">2</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">extend</span><span class="p">(</span><span class="n">u_new</span><span class="p">[</span><span class="mi">1</span><span class="p">:])</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="o">.</span><span class="n">extend</span><span class="p">(</span><span class="n">t_new</span><span class="p">[</span><span class="mi">1</span><span class="p">:])</span>
            <span class="k">if</span> <span class="n">terminate</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="nb">len</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">)</span><span class="o">-</span><span class="mi">1</span><span class="p">):</span>
                <span class="k">break</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">array</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">);</span>  <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">array</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">u_all</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">;</span>  <span class="bp">self</span><span class="o">.</span><span class="n">t_all</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

</div></div>
<div class="viewcode-block" id="RK34"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK34">[docs]</a><span class="k">class</span> <span class="nc">RK34</span><span class="p">(</span><span class="n">Adaptive</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    NOTE: This class does not work!</span>

<span class="sd">    Adaptive 4th-order Runge-Kutta method.</span>
<span class="sd">    For each time level t[n], the method takes many</span>
<span class="sd">    adaptively chosen (small) time steps to hit the</span>
<span class="sd">    next target level t[n+1].</span>
<span class="sd">    All computed u and t values are available as</span>
<span class="sd">    self.u_adaptive and self.t_adaptive, if desired.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Adaptive 4th-order Runge-Kutta method&quot;</span>

<div class="viewcode-block" id="RK34.__init__"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK34.__init__">[docs]</a>    <span class="k">def</span> <span class="nf">__init__</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="o">*</span><span class="n">args</span><span class="p">,</span> <span class="o">**</span><span class="n">kwargs</span><span class="p">):</span>
        <span class="k">raise</span> <span class="ne">Exception</span><span class="p">(</span><span class="s">&#39;Buggy code&#39;</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="RK34.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK34.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">Adaptive</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">order</span> <span class="o">=</span> <span class="mi">4</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">u_all</span> <span class="o">=</span> <span class="p">[</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="mi">0</span><span class="p">]]</span>  <span class="c"># corresponding u values</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t_all</span> <span class="o">=</span> <span class="p">[</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">]]</span>      <span class="c"># computed time levels</span>
</div>
<div class="viewcode-block" id="RK34.advance_intermediate"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK34.advance_intermediate">[docs]</a>    <span class="k">def</span> <span class="nf">advance_intermediate</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">dt</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Advance the solution an intermediate addaptive step.</span>
<span class="sd">        Parmeters: u at time t, dt is current step size.</span>
<span class="sd">        &quot;&quot;&quot;</span>

        <span class="n">f</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span>
        <span class="n">K1</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">,</span>                   <span class="n">t</span><span class="p">)</span>
        <span class="n">K2</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">K1</span><span class="o">/</span><span class="mf">2.</span><span class="p">,</span>        <span class="n">t</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.</span><span class="p">)</span>
        <span class="n">K3</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">K2</span><span class="o">/</span><span class="mf">2.</span><span class="p">,</span>        <span class="n">t</span> <span class="o">+</span> <span class="n">dt</span><span class="o">/</span><span class="mf">2.</span><span class="p">)</span>
        <span class="n">Z3</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span> <span class="o">-</span> <span class="n">dt</span><span class="o">*</span><span class="n">K1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">*</span><span class="n">dt</span><span class="o">*</span><span class="n">K2</span><span class="p">,</span> <span class="n">t</span> <span class="o">+</span> <span class="n">dt</span><span class="p">)</span>
        <span class="n">K4</span> <span class="o">=</span> <span class="n">f</span><span class="p">(</span><span class="n">u</span> <span class="o">+</span> <span class="n">dt</span><span class="o">*</span><span class="n">K3</span><span class="p">,</span>           <span class="n">t</span> <span class="o">+</span> <span class="n">dt</span><span class="p">)</span>

        <span class="n">u_new</span> <span class="o">=</span> <span class="n">dt</span><span class="o">/</span><span class="mf">6.</span><span class="o">*</span><span class="p">(</span><span class="n">K1</span> <span class="o">+</span> <span class="mi">2</span><span class="o">*</span><span class="n">K2</span> <span class="o">+</span> <span class="mi">2</span><span class="o">*</span><span class="n">K3</span> <span class="o">+</span> <span class="n">K4</span><span class="p">)</span>

        <span class="n">error</span> <span class="o">=</span> <span class="n">dt</span><span class="o">/</span><span class="mf">6.</span><span class="o">*</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">K2</span> <span class="o">+</span> <span class="n">Z3</span> <span class="o">-</span> <span class="mi">2</span><span class="o">*</span><span class="n">K3</span> <span class="o">-</span> <span class="n">K4</span><span class="p">)</span>
        <span class="n">error</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">linalg</span><span class="o">.</span><span class="n">norm</span><span class="p">(</span><span class="n">error</span><span class="p">)</span>  <span class="c"># scalar measure</span>

        <span class="k">return</span> <span class="n">u_new</span><span class="p">,</span> <span class="n">error</span>
</div>
<div class="viewcode-block" id="RK34.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RK34.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        Advance from t[n] to t[n+1] in (small) adaptive steps.</span>

<span class="sd">        Adaptivity logic:</span>
<span class="sd">        Define ``h`` as the local adaptive time step and ``dt = t[1]-t[0]``.</span>
<span class="sd">        Start with ``h`` as ``first_step`` if ``first_step &lt;= dt``,</span>
<span class="sd">        otherwise ``h = dt``.</span>
<span class="sd">        At each user-specified time level: step ``h`` forward, estimate</span>
<span class="sd">        error, accept solution if error less than tolerance, adjust ``h``,</span>
<span class="sd">        retry with new ``h`` until solution is less than error.</span>
<span class="sd">        Then proceed with a new step. Continue until next user-specified</span>
<span class="sd">        time level.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="c"># auxilatory function to pick up the middle number from 3 floats</span>
        <span class="k">def</span> <span class="nf">middle</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">z</span><span class="p">):</span>
           <span class="k">return</span> <span class="nb">sorted</span><span class="p">([</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">z</span><span class="p">])[</span><span class="mi">1</span><span class="p">]</span>

        <span class="c"># u, t: solution u at time t in between self.t[n] and self.t[n+1]</span>
        <span class="n">n</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="n">t_np1</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span>
        <span class="n">dt</span> <span class="o">=</span> <span class="n">t_np1</span> <span class="o">-</span><span class="n">t</span>

        <span class="n">min_step</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;min_step&#39;</span><span class="p">,</span> <span class="n">dt</span><span class="o">/</span><span class="mf">1000.</span><span class="p">)</span>
        <span class="n">max_step</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;max_step&#39;</span><span class="p">,</span> <span class="n">dt</span><span class="p">)</span>
        <span class="n">first_step</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;first_step&#39;</span><span class="p">,</span> <span class="n">dt</span><span class="p">)</span>
        <span class="k">if</span> <span class="n">first_step</span> <span class="o">&gt;</span> <span class="n">dt</span><span class="p">:</span>
            <span class="n">first_step</span> <span class="o">=</span> <span class="n">dt</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">h</span> <span class="o">=</span> <span class="n">first_step</span>

        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span><span class="p">:</span>
            <span class="k">print</span> <span class="s">&#39;</span><span class="se">\n</span><span class="s">advance solution in [</span><span class="si">%g</span><span class="s">, </span><span class="si">%g</span><span class="s">], &#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">t</span><span class="p">,</span> <span class="n">t_np1</span><span class="p">),</span>
            <span class="k">print</span> <span class="s">&#39;starting with h=</span><span class="si">%g</span><span class="s">&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span>

        <span class="k">while</span> <span class="n">t</span> <span class="o">&lt;</span> <span class="n">t_np1</span><span class="p">:</span>

            <span class="n">sufficiently_accurate</span> <span class="o">=</span> <span class="bp">False</span>
            <span class="k">while</span> <span class="ow">not</span> <span class="n">sufficiently_accurate</span><span class="p">:</span>
                <span class="n">u_new</span><span class="p">,</span> <span class="n">error</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">advance_intermediate</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span><span class="p">)</span>

                <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&#39;u(t=</span><span class="si">%g</span><span class="s">): </span><span class="si">%g</span><span class="s">, &#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">t</span> <span class="o">+</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span><span class="p">,</span> <span class="n">u_new</span><span class="p">),</span>

                <span class="c"># Is u_new sufficiently accurate?</span>
                <span class="n">u_new_norm</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">linalg</span><span class="o">.</span><span class="n">norm</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span>
                <span class="n">tol</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">rtol</span><span class="o">*</span><span class="n">u_new_norm</span> <span class="o">+</span> <span class="bp">self</span><span class="o">.</span><span class="n">atol</span>
                <span class="n">accurate</span> <span class="o">=</span> <span class="n">error</span> <span class="o">&lt;=</span> <span class="n">tol</span>
                <span class="k">if</span> <span class="n">accurate</span> <span class="ow">or</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span> <span class="o">&lt;=</span> <span class="n">min_step</span> <span class="ow">or</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span> <span class="o">&gt;=</span> <span class="n">max_step</span><span class="p">:</span>
                    <span class="n">sufficiently_accurate</span> <span class="o">=</span> <span class="bp">True</span>
                    <span class="n">u</span> <span class="o">=</span> <span class="n">u_new</span>
                    <span class="n">t</span> <span class="o">=</span> <span class="n">t</span> <span class="o">+</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span>
                    <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">disk_storage</span><span class="p">:</span>
                        <span class="bp">self</span><span class="o">.</span><span class="n">u_all</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">u</span><span class="p">)</span>
                    <span class="bp">self</span><span class="o">.</span><span class="n">t_all</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">t</span><span class="p">)</span>

                <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span><span class="p">:</span>
                    <span class="k">if</span> <span class="n">sufficiently_accurate</span><span class="p">:</span>
                        <span class="k">print</span> <span class="s">&#39;accepted, &#39;</span><span class="p">,</span>
                    <span class="k">else</span><span class="p">:</span>
                        <span class="k">print</span> <span class="s">&#39;rejected, &#39;</span><span class="p">,</span>
                    <span class="k">print</span> <span class="s">&#39; err=</span><span class="si">%g</span><span class="s"> (tol=</span><span class="si">%.1E</span><span class="s">), &#39;</span> <span class="o">%</span> <span class="p">(</span><span class="n">error</span><span class="p">,</span> <span class="n">tol</span><span class="p">),</span>
                    <span class="k">if</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;u_exact&#39;</span><span class="p">):</span>
                        <span class="k">print</span> <span class="s">&#39;exact-err: </span><span class="si">%g</span><span class="s">, &#39;</span> <span class="o">%</span> \
                              <span class="p">(</span><span class="n">np</span><span class="o">.</span><span class="n">abs</span><span class="p">(</span><span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u_exact</span><span class="p">(</span><span class="n">t</span><span class="p">))</span><span class="o">-</span><span class="n">u</span><span class="p">)),</span>

                <span class="c"># Adjust time step</span>
                <span class="k">if</span> <span class="n">error</span> <span class="o">&gt;</span> <span class="mf">1E-14</span><span class="p">:</span>
                    <span class="n">h_new</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span><span class="o">*</span><span class="p">(</span><span class="n">tol</span><span class="o">/</span><span class="n">error</span><span class="p">)</span><span class="o">**</span><span class="p">(</span><span class="mf">1.</span><span class="o">/</span><span class="bp">self</span><span class="o">.</span><span class="n">order</span><span class="p">)</span>
                    <span class="k">print</span> <span class="s">&#39;changing time step&#39;</span><span class="p">,</span> <span class="n">h_new</span><span class="p">,</span> <span class="n">min_step</span><span class="p">,</span> <span class="n">max_step</span>
                    <span class="bp">self</span><span class="o">.</span><span class="n">h</span> <span class="o">=</span> <span class="n">middle</span><span class="p">(</span><span class="n">min_step</span><span class="p">,</span> <span class="n">h_new</span><span class="p">,</span> <span class="n">max_step</span><span class="p">)</span>

                <span class="bp">self</span><span class="o">.</span><span class="n">h</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">h</span><span class="p">,</span> <span class="n">t_np1</span><span class="o">-</span><span class="n">t</span><span class="p">)</span>  <span class="c"># fit last step</span>

                <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">verbose</span><span class="p">:</span>
                    <span class="k">print</span> <span class="s">&#39;new h=</span><span class="si">%g</span><span class="s">&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">h</span>
        <span class="k">return</span> <span class="n">u</span>

</div></div>
<div class="viewcode-block" id="RKFehlberg"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RKFehlberg">[docs]</a><span class="k">class</span> <span class="nc">RKFehlberg</span><span class="p">(</span><span class="n">Adaptive</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    The classical adaptive Runge-Kutta-Fehlberg method of order 4-5.</span>
<span class="sd">    The method is also available in more sophisticated form as</span>
<span class="sd">    class Fehlberg (in the RungeKutta module).</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="c"># Just an example of a straightforward implementation of a classical method</span>

    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Adaptive Runge-Kutta-Fehlberg (4,5) method&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Adaptive</span><span class="o">.</span><span class="n">_optional_parameters</span>


<div class="viewcode-block" id="RKFehlberg.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.RKFehlberg.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># auxilatory function to pick up the middle number among 3 floats</span>
        <span class="k">def</span> <span class="nf">middle</span><span class="p">(</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="o">=.</span><span class="mi">1</span><span class="p">,</span> <span class="n">z</span><span class="o">=</span><span class="mf">4.</span><span class="p">):</span>
           <span class="k">return</span> <span class="nb">sorted</span><span class="p">([</span><span class="n">x</span><span class="p">,</span> <span class="n">y</span><span class="p">,</span> <span class="n">z</span><span class="p">])[</span><span class="mi">1</span><span class="p">]</span>

        <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">rtol</span><span class="p">,</span> <span class="n">atol</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">rtol</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">atol</span>
        <span class="n">h</span><span class="p">,</span> <span class="n">min_step</span><span class="p">,</span> <span class="n">max_step</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">first_step</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">min_step</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">max_step</span>
        <span class="n">u_n</span><span class="p">,</span> <span class="n">t_n</span><span class="p">,</span> <span class="n">t_np1</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span>

        <span class="n">dt</span> <span class="o">=</span> <span class="n">t_np1</span> <span class="o">-</span> <span class="n">t_n</span>

        <span class="c"># coefficients in Butcher tableau</span>
        <span class="n">c</span> <span class="o">=</span> <span class="p">(</span><span class="mi">1</span><span class="o">/</span><span class="mf">4.</span><span class="p">,</span>
             <span class="mi">3</span><span class="o">/</span><span class="mf">8.</span><span class="p">,</span>
             <span class="mi">3</span><span class="o">/</span><span class="mf">32.</span><span class="p">,</span>
             <span class="mi">9</span><span class="o">/</span><span class="mf">32.</span><span class="p">,</span>
             <span class="mi">12</span><span class="o">/</span><span class="mf">13.</span><span class="p">,</span>
             <span class="mi">1932</span><span class="o">/</span><span class="mf">2197.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">7200</span><span class="o">/</span><span class="mf">2197.</span><span class="p">,</span>
             <span class="mi">7296</span><span class="o">/</span><span class="mf">2197.</span><span class="p">,</span>
             <span class="mi">439</span><span class="o">/</span><span class="mf">216.</span><span class="p">,</span>
             <span class="o">-</span><span class="mf">8.</span><span class="p">,</span>
             <span class="mi">3680</span><span class="o">/</span><span class="mf">513.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">845</span><span class="o">/</span><span class="mf">4104.</span><span class="p">,</span>
             <span class="mi">1</span><span class="o">/</span><span class="mf">2.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">8</span><span class="o">/</span><span class="mf">27.</span><span class="p">,</span>
             <span class="mf">2.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">3544</span><span class="o">/</span><span class="mf">2565.</span><span class="p">,</span>
             <span class="mi">1859</span><span class="o">/</span><span class="mf">4104.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">11</span><span class="o">/</span><span class="mf">40.</span><span class="p">,</span>
             <span class="mi">1</span><span class="o">/</span><span class="mf">360.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">128</span><span class="o">/</span><span class="mf">4275.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">2197</span><span class="o">/</span><span class="mf">75240.</span><span class="p">,</span>
             <span class="mi">1</span><span class="o">/</span><span class="mf">50.</span><span class="p">,</span>
             <span class="mi">2</span><span class="o">/</span><span class="mf">55.</span><span class="p">,</span>
             <span class="mi">25</span><span class="o">/</span><span class="mf">216.</span><span class="p">,</span>
             <span class="mi">1408</span><span class="o">/</span><span class="mf">2565.</span><span class="p">,</span>
             <span class="mi">2197</span><span class="o">/</span><span class="mf">4104.</span><span class="p">,</span>
             <span class="o">-</span><span class="mi">1</span><span class="o">/</span><span class="mf">5.</span><span class="p">)</span>

        <span class="c"># u_i and t_i hold intermediate steps between t_n and t_np1</span>
        <span class="n">u_i</span> <span class="o">=</span> <span class="p">[</span><span class="n">u_n</span><span class="p">];</span> <span class="n">t_i</span> <span class="o">=</span> <span class="p">[</span><span class="n">t_n</span><span class="p">]</span>
        <span class="n">t</span> <span class="o">=</span> <span class="n">t_n</span>

        <span class="k">while</span> <span class="nb">abs</span><span class="p">(</span><span class="n">t</span> <span class="o">-</span> <span class="n">t_n</span><span class="p">)</span> <span class="o">&lt;</span> <span class="nb">abs</span><span class="p">(</span><span class="n">t_np1</span> <span class="o">-</span> <span class="n">t_n</span><span class="p">):</span>
            <span class="n">u</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="n">u_i</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">],</span> <span class="n">t_i</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">]</span>

            <span class="c"># internal steps</span>
            <span class="n">k1</span> <span class="o">=</span> <span class="n">h</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">)</span>
            <span class="n">k2</span> <span class="o">=</span> <span class="n">h</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="o">+</span><span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">0</span><span class="p">],</span> <span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
            <span class="n">k3</span> <span class="o">=</span> <span class="n">h</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="o">+</span><span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">2</span><span class="p">]</span><span class="o">+</span><span class="n">k2</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">3</span><span class="p">],</span> <span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">1</span><span class="p">])</span>
            <span class="n">k4</span> <span class="o">=</span> <span class="n">h</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="o">+</span><span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">5</span><span class="p">]</span><span class="o">+</span><span class="n">k2</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">6</span><span class="p">]</span><span class="o">+</span><span class="n">k3</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">7</span><span class="p">],</span> <span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">4</span><span class="p">])</span>
            <span class="n">k5</span> <span class="o">=</span> <span class="n">h</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="o">+</span><span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">8</span><span class="p">]</span><span class="o">+</span><span class="n">k2</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">9</span><span class="p">]</span><span class="o">+</span><span class="n">k3</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">10</span><span class="p">]</span><span class="o">+</span><span class="n">k4</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">11</span><span class="p">],</span> <span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="p">)</span>
            <span class="n">k6</span> <span class="o">=</span> <span class="n">h</span><span class="o">*</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="o">+</span><span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">13</span><span class="p">]</span><span class="o">+</span><span class="n">k2</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">14</span><span class="p">]</span><span class="o">+</span><span class="n">k3</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">15</span><span class="p">]</span><span class="o">+</span><span class="n">k4</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">16</span><span class="p">]</span><span class="o">+</span><span class="n">k5</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">17</span><span class="p">],</span>
                     <span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">12</span><span class="p">])</span>
            <span class="n">u_new</span> <span class="o">=</span> <span class="n">u</span> <span class="o">+</span> <span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">23</span><span class="p">]</span> <span class="o">+</span> <span class="n">k3</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">24</span><span class="p">]</span> <span class="o">+</span> <span class="n">k4</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">25</span><span class="p">]</span> <span class="o">+</span> <span class="n">k5</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">26</span><span class="p">]</span>

            <span class="c"># local error between 2 levels</span>
            <span class="n">error</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">abs</span><span class="p">(</span><span class="n">k1</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">18</span><span class="p">]</span> <span class="o">+</span> <span class="n">k3</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">19</span><span class="p">]</span> <span class="o">+</span> <span class="n">k4</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">20</span><span class="p">]</span> <span class="o">+</span> \
                          <span class="n">k5</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">21</span><span class="p">]</span> <span class="o">+</span> <span class="n">k6</span><span class="o">*</span><span class="n">c</span><span class="p">[</span><span class="mi">22</span><span class="p">])</span>
            <span class="n">tol</span> <span class="o">=</span> <span class="n">rtol</span><span class="o">*</span><span class="n">np</span><span class="o">.</span><span class="n">abs</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span> <span class="o">+</span> <span class="n">atol</span>
            <span class="c"># Error factor = local-error/error-tolerance</span>
            <span class="n">rms</span> <span class="o">=</span> <span class="n">error</span><span class="o">/</span><span class="n">tol</span>
            <span class="n">rms_norm</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">sqrt</span><span class="p">((</span><span class="n">np</span><span class="o">.</span><span class="n">sum</span><span class="p">(</span><span class="n">rms</span><span class="o">*</span><span class="n">rms</span><span class="p">))</span><span class="o">/</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">)</span>

            <span class="c"># Close enough or step size can not be reduced any more</span>
            <span class="k">if</span> <span class="n">rms_norm</span> <span class="o">&lt;=</span> <span class="mf">1.</span> <span class="ow">or</span> <span class="n">h</span> <span class="o">&lt;=</span> <span class="n">min_step</span><span class="p">:</span>
                <span class="n">u_i</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span>
                <span class="n">t_i</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="p">)</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">u_all</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">t_all</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">t</span><span class="o">+</span><span class="n">h</span><span class="p">)</span>

            <span class="c"># prevent the error of dividing absolute zero</span>
            <span class="n">error</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">([(</span><span class="mf">1e-16</span> <span class="k">if</span> <span class="n">x</span> <span class="o">==</span> <span class="mf">0.</span> <span class="k">else</span> <span class="n">x</span><span class="p">)</span> <span class="k">for</span> <span class="n">x</span> <span class="ow">in</span> <span class="n">error</span><span class="p">])</span> \
                   <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">&gt;</span> <span class="mi">1</span> <span class="k">else</span> <span class="p">(</span><span class="mf">1e-16</span> <span class="k">if</span> <span class="n">error</span> <span class="o">==</span> <span class="mf">0.</span> <span class="k">else</span> <span class="n">error</span><span class="p">)</span>

            <span class="c"># Factor to adjust next step size</span>
            <span class="n">s</span> <span class="o">=</span> <span class="p">(</span><span class="n">tol</span><span class="o">/</span><span class="p">(</span><span class="mi">2</span><span class="o">*</span><span class="n">error</span><span class="p">))</span><span class="o">**</span><span class="mf">0.25</span>
            <span class="c"># Factor should be in a reasonable range[0.1,4.0]</span>
            <span class="n">s</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="nb">map</span><span class="p">(</span><span class="n">middle</span><span class="p">,</span> <span class="n">s</span><span class="p">))</span> <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">&gt;</span> <span class="mi">1</span> <span class="k">else</span> <span class="n">middle</span><span class="p">(</span><span class="n">s</span><span class="p">)</span>

            <span class="c"># Step size should be in range [min_step, max_step]</span>
            <span class="n">h</span> <span class="o">=</span> <span class="n">middle</span><span class="p">(</span><span class="n">h</span><span class="o">*</span><span class="n">s</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">min_step</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">max_step</span><span class="p">)</span>

            <span class="c"># h should be set to &#39;t_np1-t_i[-1]&#39; at the last intern step.</span>
            <span class="n">h</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="n">h</span><span class="p">,</span> <span class="n">t_np1</span><span class="o">-</span><span class="n">t_i</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span>

        <span class="k">return</span> <span class="n">u_new</span>

</div></div>
<div class="viewcode-block" id="ode_scipy"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ode_scipy">[docs]</a><span class="k">class</span> <span class="nc">ode_scipy</span><span class="p">(</span><span class="n">Adaptive</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Superclass wrapper for ``scipy.integrate.ode`` classes.</span>
<span class="sd">    Existing solvers in subclasses are: ``Vode``, ``Dopri5``, ``Dop853``.</span>
<span class="sd">    &quot;&quot;&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Adaptive</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="s">&#39;jac_kwargs&#39;</span><span class="p">,</span> <span class="s">&#39;jac_args&#39;</span><span class="p">,</span> <span class="s">&#39;nsteps&#39;</span><span class="p">]</span>

    <span class="c"># Common scipy.integrate.ode arguments for subclass solvers</span>
    <span class="n">_arglist_scipy</span> <span class="o">=</span> <span class="p">[</span><span class="s">&#39;f&#39;</span><span class="p">,</span> <span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="s">&#39;atol&#39;</span><span class="p">,</span> <span class="s">&#39;rtol&#39;</span><span class="p">,</span> <span class="s">&#39;complex_valued&#39;</span><span class="p">,]</span>
    <span class="c"># Name differences between this interface and scipy arguments</span>
    <span class="n">_name_differences</span> <span class="o">=</span> <span class="p">{</span><span class="s">&#39;adams_or_bdf&#39;</span><span class="p">:</span> <span class="s">&#39;method&#39;</span><span class="p">,</span>
                         <span class="s">&#39;ml&#39;</span><span class="p">:</span> <span class="s">&#39;lband&#39;</span><span class="p">,</span> <span class="s">&#39;mu&#39;</span><span class="p">:</span> <span class="s">&#39;rband&#39;</span><span class="p">}</span>

<div class="viewcode-block" id="ode_scipy.initialize"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ode_scipy.initialize">[docs]</a>    <span class="k">def</span> <span class="nf">initialize</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">try</span><span class="p">:</span>
            <span class="kn">import</span> <span class="nn">scipy.integrate.ode</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">scipy_ode</span> <span class="o">=</span> <span class="n">scipy</span><span class="o">.</span><span class="n">integrate</span><span class="o">.</span><span class="n">ode</span>
        <span class="k">except</span> <span class="ne">ImportError</span><span class="p">:</span>
            <span class="k">raise</span> <span class="ne">ImportError</span><span class="p">(</span><span class="s">&#39;The scipy package must be installed &#39;</span>\
                              <span class="s">&#39;in order to use class </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                              <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="ode_scipy.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ode_scipy.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># scipy specifies f and jac as f(t, y, *args) and jac(t, y)</span>
        <span class="c"># while the present interface assumes</span>
        <span class="c"># f(u, t, *f_args, **f_kwargs), jac(u, t, *jac_args, **jac_kwargs)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f4scipy</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">t</span><span class="p">,</span> <span class="n">y</span><span class="p">:</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">(</span><span class="n">y</span><span class="p">,</span> <span class="n">t</span><span class="p">)</span>
        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">jac</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span>
            <span class="c"># First wrap the user&#39;s Jacobian routine as we wrap f</span>
            <span class="c"># (allow jac to return list of lists)</span>
            <span class="n">jac</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">jac</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">jac</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">:</span> \
                <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">jac</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">jac_args</span><span class="p">,</span> <span class="o">**</span><span class="bp">self</span><span class="o">.</span><span class="n">jac_kwargs</span><span class="p">))</span>
            <span class="c"># Then switch argument sequence</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">jac4scipy</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">t</span><span class="p">,</span> <span class="n">y</span><span class="p">:</span> <span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">(</span><span class="n">y</span><span class="p">,</span> <span class="n">t</span><span class="p">)</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">jac4scipy</span> <span class="o">=</span> <span class="bp">None</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">scipy_ode</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">f4scipy</span><span class="p">,</span> <span class="n">jac</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">jac4scipy</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">scipy_arguments</span> <span class="o">=</span> <span class="p">{}</span>

        <span class="c"># Extract common arguments, and prepare to be transferred to scipy</span>
        <span class="k">for</span> <span class="n">name</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_arglist_scipy</span><span class="p">:</span>
            <span class="n">value</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">name</span><span class="p">,</span> <span class="bp">None</span><span class="p">)</span>
            <span class="k">if</span> <span class="n">value</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span>
                <span class="k">if</span> <span class="n">name</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">_parameters</span> <span class="ow">and</span> \
                   <span class="n">name</span> <span class="ow">in</span> <span class="n">ode_scipy</span><span class="o">.</span><span class="n">_name_differences</span><span class="p">:</span>
                    <span class="c"># different names in scipy</span>
                    <span class="n">name</span> <span class="o">=</span> <span class="n">ode_scipy</span><span class="o">.</span><span class="n">_name_differences</span><span class="p">[</span><span class="n">name</span><span class="p">]</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">scipy_arguments</span><span class="p">[</span><span class="n">name</span><span class="p">]</span> <span class="o">=</span> <span class="n">value</span>

        <span class="n">scipy_ode_classname</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="o">.</span><span class="n">lower</span><span class="p">()</span>
        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">complex_valued</span> <span class="ow">and</span> <span class="n">scipy_ode_classname</span> <span class="o">==</span> <span class="s">&#39;vode&#39;</span><span class="p">:</span>
            <span class="n">scipy_ode_classname</span> <span class="o">=</span> <span class="s">&#39;zvode&#39;</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span><span class="o">.</span><span class="n">set_integrator</span><span class="p">(</span>
            <span class="n">scipy_ode_classname</span><span class="p">,</span> <span class="o">**</span><span class="bp">self</span><span class="o">.</span><span class="n">scipy_arguments</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span><span class="o">.</span><span class="n">set_initial_value</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">])</span>
        <span class="n">Adaptive</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="ode_scipy.advance"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.ode_scipy.advance">[docs]</a>    <span class="k">def</span> <span class="nf">advance</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="n">u</span><span class="p">,</span> <span class="n">f</span><span class="p">,</span> <span class="n">n</span><span class="p">,</span> <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">n</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>
        <span class="n">u_new</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span><span class="o">.</span><span class="n">integrate</span><span class="p">(</span><span class="n">t</span><span class="p">[</span><span class="n">n</span><span class="o">+</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="bp">self</span><span class="o">.</span><span class="n">integrator</span><span class="o">.</span><span class="n">successful</span><span class="p">():</span>
            <span class="k">print</span> <span class="s">&#39;Warning: </span><span class="si">%s</span><span class="s"> call to scipy.integrate.ode.method.integrate was not successful&#39;</span> <span class="o">%</span> <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span>
        <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">u_new</span><span class="p">)</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
            <span class="k">return</span> <span class="n">u_new</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span>
        <span class="k">else</span><span class="p">:</span>
            <span class="k">return</span> <span class="n">u_new</span>
</div></div>
<div class="viewcode-block" id="Vode"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Vode">[docs]</a><span class="k">class</span> <span class="nc">Vode</span><span class="p">(</span><span class="n">ode_scipy</span><span class="p">):</span>
    <span class="sd">&#39;&#39;&#39;</span>
<span class="sd">    Wrapper for scipy.integrate.ode.vode, which is a wrapper for vode.f,</span>
<span class="sd">    which intends to solve initial value problems of stiff or nonstiff</span>
<span class="sd">    type. The well-known vode.f solver applies backward differential</span>
<span class="sd">    formulae for iteration.</span>
<span class="sd">    &#39;&#39;&#39;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Adams/BDF Vode adaptive method (vode.f wrapper)&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">ode_scipy</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
                           <span class="p">[</span><span class="s">&#39;adams_or_bdf&#39;</span><span class="p">,</span> <span class="s">&#39;min_step&#39;</span><span class="p">,</span> <span class="s">&#39;order&#39;</span><span class="p">]</span>

    <span class="c"># argument list to be passed to scipy.ode for &#39;vode&#39; method</span>
    <span class="n">_arglist_scipy</span> <span class="o">=</span> <span class="p">[</span><span class="s">&#39;atol&#39;</span><span class="p">,</span> <span class="s">&#39;rtol&#39;</span><span class="p">,</span> <span class="s">&#39;ml&#39;</span><span class="p">,</span> <span class="s">&#39;mu&#39;</span><span class="p">,</span> <span class="s">&#39;adams_or_bdf&#39;</span><span class="p">,</span>
                      <span class="s">&#39;with_jacobian&#39;</span><span class="p">,</span> <span class="s">&#39;nsteps&#39;</span><span class="p">,</span> <span class="s">&#39;first_step&#39;</span><span class="p">,</span>
                      <span class="s">&#39;min_step&#39;</span><span class="p">,</span> <span class="s">&#39;max_step&#39;</span><span class="p">,</span> <span class="s">&#39;order&#39;</span><span class="p">]</span>

<div class="viewcode-block" id="Vode.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Vode.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># internal argument to be transferred to scipy</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">with_jacobian</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="bp">None</span><span class="p">)</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span>
        <span class="n">ode_scipy</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>
</div></div>
<div class="viewcode-block" id="Dopri5"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Dopri5">[docs]</a><span class="k">class</span> <span class="nc">Dopri5</span><span class="p">(</span><span class="n">ode_scipy</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Wrapper for scipy.integrate.ode.dopri5, which applies the</span>
<span class="sd">    Dormand&amp;Prince method of order 5(4), based on the Fortran</span>
<span class="sd">    implementation by Hairer and Wanner.</span>
<span class="sd">    See http://www.unige.ch/~hairer/software.html.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Dormand &amp; Prince method of order 5(4) (scipy)&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">ode_scipy</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;ifactor&#39;</span><span class="p">,</span> <span class="s">&#39;dfactor&#39;</span><span class="p">,</span> <span class="s">&#39;beta&#39;</span><span class="p">,</span> <span class="s">&#39;safety&#39;</span><span class="p">]</span>

    <span class="c"># argument list to be passed to scipy.ode for &#39;dopri5&#39; method</span>
    <span class="n">_arglist_scipy</span> <span class="o">=</span> <span class="p">(</span><span class="s">&#39;atol&#39;</span><span class="p">,</span><span class="s">&#39;rtol&#39;</span><span class="p">,</span><span class="s">&#39;safety&#39;</span><span class="p">,</span><span class="s">&#39;ifactor&#39;</span><span class="p">,</span><span class="s">&#39;dfactor&#39;</span><span class="p">,</span><span class="s">&#39;beta&#39;</span><span class="p">,</span>
                      <span class="s">&#39;nsteps&#39;</span><span class="p">,</span><span class="s">&#39;first_step&#39;</span><span class="p">,</span><span class="s">&#39;max_step&#39;</span><span class="p">)</span>
</div>
<div class="viewcode-block" id="Dop853"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.Dop853">[docs]</a><span class="k">class</span> <span class="nc">Dop853</span><span class="p">(</span><span class="n">ode_scipy</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Wrapper for scipy.integrate.ode.dop853, which applies the</span>
<span class="sd">    Dormand&amp;Prince method of order 8(5,3), based on the Fortran</span>
<span class="sd">    implementation by Hairer and Wanner.</span>
<span class="sd">    See http://www.unige.ch/~hairer/software.html.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Adaptive Dormand &amp; Prince method of order 8(5,3) (scipy)&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">ode_scipy</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;ifactor&#39;</span><span class="p">,</span> <span class="s">&#39;dfactor&#39;</span><span class="p">,</span> <span class="s">&#39;beta&#39;</span><span class="p">,</span> <span class="s">&#39;safety&#39;</span><span class="p">]</span>

    <span class="c"># argument list to be passed to scipy.ode for &#39;dop853&#39; method</span>
    <span class="n">_arglist_scipy</span> <span class="o">=</span> <span class="p">(</span><span class="s">&#39;atol&#39;</span><span class="p">,</span><span class="s">&#39;rtol&#39;</span><span class="p">,</span><span class="s">&#39;safety&#39;</span><span class="p">,</span><span class="s">&#39;ifactor&#39;</span><span class="p">,</span><span class="s">&#39;dfactor&#39;</span><span class="p">,</span><span class="s">&#39;beta&#39;</span><span class="p">,</span>
                      <span class="s">&#39;nsteps&#39;</span><span class="p">,</span><span class="s">&#39;first_step&#39;</span><span class="p">,</span><span class="s">&#39;max_step&#39;</span><span class="p">)</span>

</div>
<div class="viewcode-block" id="lsoda_scipy"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.lsoda_scipy">[docs]</a><span class="k">class</span> <span class="nc">lsoda_scipy</span><span class="p">(</span><span class="n">Adaptive</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Wrapper of the scipy.integrate.odeint solver so that it can be</span>
<span class="sd">    called from the *odespy* user interface.</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;Wrapper of lsoda (scipy.integrate.odeint)&quot;</span>

    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Adaptive</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="s">&#39;jac_kwargs&#39;</span><span class="p">,</span> <span class="s">&#39;jac_args&#39;</span><span class="p">,</span> <span class="s">&#39;ml&#39;</span><span class="p">,</span> <span class="s">&#39;mu&#39;</span><span class="p">,]</span>

<div class="viewcode-block" id="lsoda_scipy.initialize"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.lsoda_scipy.initialize">[docs]</a>    <span class="k">def</span> <span class="nf">initialize</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">try</span><span class="p">:</span>
            <span class="kn">import</span> <span class="nn">scipy.integrate</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">scipy_int</span> <span class="o">=</span> <span class="n">scipy</span><span class="o">.</span><span class="n">integrate</span>
        <span class="k">except</span> <span class="ne">ImportError</span><span class="p">:</span>
            <span class="k">raise</span> <span class="ne">ImportError</span><span class="p">(</span><span class="s">&#39;The scipy package must be installed &#39;</span>\
                              <span class="s">&#39;in order to use class </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                              <span class="bp">self</span><span class="o">.</span><span class="n">__class__</span><span class="o">.</span><span class="n">__name__</span><span class="p">)</span>

    <span class="c">#def initialize_for_solve(self):</span>
    <span class="c"># odeint applies f(u,t) and jac(u,t)</span>
    <span class="c"># min_step etc are adequately computed</span>
</div>
<div class="viewcode-block" id="lsoda_scipy.solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.lsoda_scipy.solve">[docs]</a>    <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">time_points</span><span class="p">,</span> <span class="n">terminate</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">()</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">validate_data</span><span class="p">()</span>

        <span class="c"># jac_banded is not yet supported</span>
        <span class="n">ml</span> <span class="o">=</span> <span class="bp">None</span>  <span class="c"># self.ml</span>
        <span class="n">mu</span> <span class="o">=</span> <span class="bp">None</span>  <span class="c"># self.mu</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="n">info</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">scipy_int</span><span class="o">.</span><span class="n">odeint</span><span class="p">(</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">,</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">,</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span>
            <span class="n">Dfun</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">jac</span><span class="p">,</span>
            <span class="c">#ml=ml,</span>
            <span class="c">#mu=mu,</span>
            <span class="n">full_output</span><span class="o">=</span><span class="bp">True</span><span class="p">,</span>
            <span class="n">rtol</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">rtol</span><span class="p">,</span>
            <span class="n">atol</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">atol</span><span class="p">,</span>
            <span class="c">#h0=self.first_step,  # NOTE: does not work well!</span>
            <span class="n">hmin</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">min_step</span><span class="p">,</span>
            <span class="n">hmax</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">max_step</span><span class="p">,</span>
            <span class="p">)</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">info</span> <span class="o">=</span> \
        <span class="p">{</span><span class="s">&#39;hu&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;hu&#39;</span><span class="p">],</span>
                <span class="s">&#39;vector of step sizes successfully used for each time step.&#39;</span><span class="p">),</span>
         <span class="s">&#39;tcur&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;tcur&#39;</span><span class="p">],</span>
                  <span class="s">&#39;vector with the value of t reached for each time step. &#39;</span>\
                  <span class="s">&#39;(will always be at least as large as the input times).&#39;</span><span class="p">),</span>
         <span class="s">&#39;tolsf&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;tolsf&#39;</span><span class="p">],</span>
                   <span class="s">&#39;vector of tolerance scale factors, greater than 1.0, &#39;</span>\
                   <span class="s">&#39;computed when a request for too much accuracy was detected.&#39;</span><span class="p">),</span>
         <span class="s">&#39;tsw&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;tsw&#39;</span><span class="p">],</span>
                 <span class="s">&#39;value of t at the time of the last method. &#39;</span>\
                 <span class="s">&#39;switch (given for each time step).&#39;</span><span class="p">),</span>
         <span class="s">&#39;nst&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;nst&#39;</span><span class="p">],</span>
                 <span class="s">&#39;cumulative number of time steps&#39;</span><span class="p">),</span>
         <span class="s">&#39;nfe&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;nfe&#39;</span><span class="p">],</span>
                 <span class="s">&#39;cumulative number of function evaluations for each time step&#39;</span><span class="p">),</span>
         <span class="s">&#39;nje&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;nje&#39;</span><span class="p">],</span>
                 <span class="s">&#39;cumulative number of jacobian evaluations for each time step&#39;</span><span class="p">),</span>
         <span class="s">&#39;nqu&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;nqu&#39;</span><span class="p">],</span>
                 <span class="s">&#39;a vector of method orders for each successful step.&#39;</span><span class="p">),</span>
         <span class="s">&#39;imxer&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;imxer&#39;</span><span class="p">],</span>
                   <span class="s">&#39;index of the component of largest magnitude in the &#39;</span>\
                   <span class="s">&#39;weighted local error vector (e / ewt) on an error &#39;</span>\
                   <span class="s">&#39;return, -1 otherwise.&#39;</span><span class="p">),</span>
         <span class="s">&#39;lenrw&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;lenrw&#39;</span><span class="p">],</span>
                   <span class="s">&#39;the length of the double work array required.&#39;</span><span class="p">),</span>
         <span class="s">&#39;leniw&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;leniw&#39;</span><span class="p">],</span>
                   <span class="s">&#39;the length of integer work array required.&#39;</span><span class="p">),</span>
         <span class="s">&#39;mused&#39;</span><span class="p">:</span> <span class="p">(</span><span class="n">info</span><span class="p">[</span><span class="s">&#39;mused&#39;</span><span class="p">],</span>
                   <span class="s">&#39;a vector of method indicators for each successful &#39;</span>\
                   <span class="s">&#39;time step: 1: adams (nonstiff), 2: bdf (stiff)&#39;</span><span class="p">)</span>
         <span class="p">}</span>

        <span class="c"># self.u is two-dimensional, remove 2nd dimension if scalar ODE</span>
        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">shape</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">u</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">reshape</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="o">.</span><span class="n">size</span><span class="p">)</span>

        <span class="k">if</span> <span class="n">terminate</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span>
            <span class="k">for</span> <span class="n">step_no</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="nb">len</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">)):</span>
                <span class="k">if</span> <span class="n">terminate</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">,</span> <span class="n">step_no</span><span class="p">):</span>
                    <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[:</span><span class="n">step_no</span><span class="o">+</span><span class="mi">1</span><span class="p">],</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[:</span><span class="n">step_no</span><span class="o">+</span><span class="mi">1</span><span class="p">]</span>

        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>

</div></div>
<div class="viewcode-block" id="odelab"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odelab">[docs]</a><span class="k">class</span> <span class="nc">odelab</span><span class="p">(</span><span class="n">Adaptive</span><span class="p">):</span>
    <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">    Odespy wrapper for the odelab package.</span>
<span class="sd">    Typical use::</span>

<span class="sd">        f = lambda u: -u   # u&#39; = -u</span>
<span class="sd">        import odespy, numpy</span>
<span class="sd">        solver = odespy.odelab(f, odelab_solver=&#39;Butcher&#39;)</span>
<span class="sd">        solver.set_initial_condition(1.0)</span>
<span class="sd">        u, t = solver.solve(numpy.linspace(0, 3, 21))</span>

<span class="sd">    Odelab offers the following solvers (for parameter ``odelab_solver``):</span>
<span class="sd">    %s</span>

<span class="sd">    Note: ode15s is actually scipy&#39;s vode code called with BDF order=5.</span>
<span class="sd">    Odelab&#39;s DAE methods are not yet supported (could be by proper</span>
<span class="sd">    wrapping of f and g in an ``odelab.system.System object``).</span>
<span class="sd">    &quot;&quot;&quot;</span>
    <span class="n">quick_description</span> <span class="o">=</span> <span class="s">&quot;interface to all solvers in odelab&quot;</span>

    <span class="n">_required_parameters</span> <span class="o">=</span> <span class="n">Adaptive</span><span class="o">.</span><span class="n">_required_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;odelab_solver&#39;</span><span class="p">]</span>
    <span class="n">_optional_parameters</span> <span class="o">=</span> <span class="n">Adaptive</span><span class="o">.</span><span class="n">_optional_parameters</span> <span class="o">+</span> \
        <span class="p">[</span><span class="s">&#39;jac&#39;</span><span class="p">,</span> <span class="s">&#39;jac_args&#39;</span><span class="p">,</span> <span class="s">&#39;jac_kwargs&#39;</span><span class="p">,</span> <span class="p">]</span>

    <span class="n">solvers</span> <span class="o">=</span> <span class="s">&#39;ExplicitEuler ExplicitTrapezoidal ImplicitEuler RungeKutta34 RungeKutta4 SymplecticEuler ImplicitEuler LDIRK343 LobattoIIIA LobattoIIIB LobattoIIIC LobattoIIICs LobattoIIID MultiRKDAE RKDAE RadauIIA RungeKutta Spark Spark2 Spark3 Spark4 AdamsBashforth AdamsBashforth1 AdamsBashforth2 AdamsBashforth2e Butcher Butcher1 Butcher3 ExplicitGeneralLinear GeneralLinear Heun Kutta Kutta38 Kutta4 McLachlan NonHolonomicEnergy NonHolonomicEnergy0 NonHolonomicEnergyEMP NonHolonomicLeapFrog SymplecticEuler ABLawson ABLawson2 ABLawson3 ABLawson4 ABNorset4 Exponential GenLawson45 HochOst4 Lawson4 LawsonEuler Phi Polynomial RKMK4T&#39;</span><span class="o">.</span><span class="n">split</span><span class="p">()</span>
    <span class="n">DAE_solvers</span> <span class="o">=</span> <span class="s">&#39;SymplicticEuler MultiRKDAE RKDAE Spark Spark2 Spark3 Spark4&#39;</span><span class="o">.</span><span class="n">split</span><span class="p">()</span>
    <span class="n">not_valid</span> <span class="o">=</span> <span class="s">&#39;SymplecticEuler LDIRK343 LobattoIIIA LobattoIIIB LobattoIIIC LobattoIIICs LobattoIIID MultiRKDAE RKDAE RadauIIA RungeKutta Spark Spark2 Spark3 Spark4 AdamsBashforth AdamsBashforth2 AdamsBashforth2e Butcher Butcher1 Butcher3 ExplicitGeneralLinear GeneralLinear Kutta McLachlan NonHolonomicEnergy NonHolonomicEnergy0 NonHolonomicEnergyEMP NonHolonomicLeapFrog SymplecticEuler ABLawson ABLawson2 ABLawson3 ABLawson4 ABNorset4 Exponential GenLawson45 HochOst4 Lawson4 LawsonEuler Phi Polynomial RKMK4T&#39;</span><span class="o">.</span><span class="n">split</span><span class="p">()</span>
    <span class="n">solvers</span> <span class="o">=</span> <span class="p">[</span><span class="n">solver</span> <span class="k">for</span> <span class="n">solver</span> <span class="ow">in</span> <span class="n">solvers</span> <span class="k">if</span> <span class="ow">not</span> <span class="n">solver</span> <span class="ow">in</span> <span class="n">not_valid</span><span class="p">]</span>

    <span class="n">__doc__</span> <span class="o">=</span> <span class="n">__doc__</span> <span class="o">%</span> <span class="p">(</span><span class="nb">str</span><span class="p">(</span><span class="n">solvers</span><span class="p">)[</span><span class="mi">1</span><span class="p">:</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span>

<div class="viewcode-block" id="odelab.initialize"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odelab.initialize">[docs]</a>    <span class="k">def</span> <span class="nf">initialize</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="k">try</span><span class="p">:</span>
            <span class="kn">import</span> <span class="nn">odelab</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">odelab</span> <span class="o">=</span> <span class="n">odelab</span>
            <span class="kn">import</span> <span class="nn">odelab.scheme.classic</span><span class="o">,</span> \
                   <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">geometric</span><span class="p">,</span> \
                   <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">rungekutta</span><span class="p">,</span> \
                   <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">generallinear</span><span class="p">,</span> \
                   <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">constrained</span><span class="p">,</span> \
                   <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">exponential</span><span class="p">,</span> \
                   <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span>

            <span class="bp">self</span><span class="o">.</span><span class="n">odelab_scheme_modules</span> <span class="o">=</span> <span class="p">[</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">classic</span><span class="p">,</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">geometric</span><span class="p">,</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">rungekutta</span><span class="p">,</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">generallinear</span><span class="p">,</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">constrained</span><span class="p">,</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="o">.</span><span class="n">exponential</span><span class="p">,</span>
                <span class="n">odelab</span><span class="o">.</span><span class="n">scheme</span><span class="p">,</span>
                <span class="p">]</span>

            <span class="c"># Rough way of extracting scheme classes in odelab</span>
            <span class="n">schemes</span> <span class="o">=</span> <span class="p">[]</span>
            <span class="k">for</span> <span class="n">m</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab_scheme_modules</span><span class="p">:</span>
                <span class="k">for</span> <span class="n">e</span> <span class="ow">in</span> <span class="nb">dir</span><span class="p">(</span><span class="n">m</span><span class="p">):</span>
                    <span class="k">if</span> <span class="n">e</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span><span class="o">.</span><span class="n">isupper</span><span class="p">()</span> <span class="ow">and</span> <span class="n">e</span> <span class="o">!=</span> <span class="s">&#39;Scheme&#39;</span> <span class="ow">and</span> <span class="s">&#39;Error&#39;</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">e</span><span class="p">:</span>
                        <span class="n">schemes</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">e</span><span class="p">)</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">odelab_schemes</span> <span class="o">=</span> <span class="n">schemes</span>

        <span class="k">except</span> <span class="ne">ImportError</span><span class="p">:</span>
            <span class="k">raise</span> <span class="ne">ImportError</span><span class="p">,</span><span class="s">&#39;The odelab software is not installed - needed for class odelab&#39;</span>
</div>
<div class="viewcode-block" id="odelab.initialize_for_solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odelab.initialize_for_solve">[docs]</a>    <span class="k">def</span> <span class="nf">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">):</span>
        <span class="c"># odelab requires f(t, u), not f(u, t, *args, **kwargs)</span>
        <span class="c"># self.f4odelab(t, u) is what we pass on to odelab</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">f4odelab</span> <span class="o">=</span> <span class="k">lambda</span> <span class="n">t</span><span class="p">,</span> <span class="n">u</span><span class="p">:</span> <span class="bp">self</span><span class="o">.</span><span class="n">f</span><span class="p">(</span><span class="n">u</span><span class="p">,</span> <span class="n">t</span><span class="p">,</span> <span class="o">*</span><span class="bp">self</span><span class="o">.</span><span class="n">f_args</span><span class="p">,</span> <span class="o">**</span><span class="bp">self</span><span class="o">.</span><span class="n">f_kwargs</span><span class="p">)</span>
        <span class="n">Solver</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">(</span><span class="bp">self</span><span class="p">)</span>

        <span class="c">#if self.odelab_solver not in odelab.solvers:</span>
        <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab_solver</span> <span class="ow">not</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab_schemes</span><span class="p">:</span>
            <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&#39;requested solver </span><span class="si">%s</span><span class="s"> not legal.</span><span class="se">\n</span><span class="s">Legal: </span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                             <span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">odelab_solver</span><span class="p">,</span> <span class="nb">str</span><span class="p">(</span><span class="n">odelab</span><span class="o">.</span><span class="n">solvers</span><span class="p">)))</span>

        <span class="bp">self</span><span class="o">.</span><span class="n">system</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab</span><span class="o">.</span><span class="n">System</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">f4odelab</span><span class="p">)</span>

        <span class="n">h</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">1</span><span class="p">]</span> <span class="o">-</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span>
        <span class="c"># odelab solvers are in different modules</span>
        <span class="k">for</span> <span class="n">module</span> <span class="ow">in</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab_scheme_modules</span><span class="p">:</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab_solver</span> <span class="ow">in</span> <span class="nb">dir</span><span class="p">(</span><span class="n">module</span><span class="p">):</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">scheme</span> <span class="o">=</span> <span class="nb">getattr</span><span class="p">(</span><span class="n">module</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab_solver</span><span class="p">)(</span><span class="n">h</span><span class="p">)</span>
                <span class="k">break</span>
        <span class="k">if</span> <span class="ow">not</span> <span class="nb">hasattr</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="s">&#39;scheme&#39;</span><span class="p">):</span>
            <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="s">&#39;</span><span class="si">%s</span><span class="s"> is not a scheme in odelab</span><span class="se">\n</span><span class="s">(</span><span class="si">%s</span><span class="s">)&#39;</span> <span class="o">%</span>
                             <span class="s">&#39;, &#39;</span><span class="o">.</span><span class="n">join</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">odelab_schemes</span><span class="p">))</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">solver</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">odelab</span><span class="o">.</span><span class="n">Solver</span><span class="p">(</span><span class="n">scheme</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">scheme</span><span class="p">,</span>
                                         <span class="n">system</span><span class="o">=</span><span class="bp">self</span><span class="o">.</span><span class="n">system</span><span class="p">)</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">tol</span> <span class="o">=</span> <span class="nb">min</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">rtol</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">atol</span><span class="p">)</span>
        <span class="c"># No way to give Jacobian to odelab?</span>

</div>
<div class="viewcode-block" id="odelab.solve"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.odelab.solve">[docs]</a>    <span class="k">def</span> <span class="nf">solve</span><span class="p">(</span><span class="bp">self</span><span class="p">,</span> <span class="n">time_points</span><span class="p">,</span> <span class="n">terminate</span><span class="o">=</span><span class="bp">None</span><span class="p">):</span>
        <span class="sd">&quot;&quot;&quot;</span>
<span class="sd">        The complete solve method must be overridded in this class</span>
<span class="sd">        since odelab. is such a solve method.</span>
<span class="sd">        &quot;&quot;&quot;</span>
        <span class="k">if</span> <span class="n">terminate</span> <span class="ow">is</span> <span class="ow">not</span> <span class="bp">None</span><span class="p">:</span>
            <span class="k">print</span> <span class="s">&#39;Warning: odelab.solve ignores the terminate function!&#39;</span>
        <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">np</span><span class="o">.</span><span class="n">asarray</span><span class="p">(</span><span class="n">time_points</span><span class="p">)</span>

        <span class="k">try</span><span class="p">:</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">initialize_for_solve</span><span class="p">()</span>
            <span class="c"># Note allocating self.u based on self.t, as done in</span>
            <span class="c"># Solver.initialize_for_solve, is not correct for adaptive</span>
            <span class="c"># methods so we have to reallocate self.u below.</span>

            <span class="c"># Set initial condition</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">initialize</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">U0</span><span class="p">)</span>
            <span class="c"># Solve problem in odelab</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">run</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">[</span><span class="o">-</span><span class="mi">1</span><span class="p">])</span>
        <span class="k">except</span> <span class="ne">Exception</span><span class="p">,</span> <span class="n">e</span><span class="p">:</span>
            <span class="n">msg</span> <span class="o">=</span> <span class="s">&#39;odelab scheme </span><span class="si">%s</span><span class="s"> did not work:</span><span class="se">\n</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> \
                  <span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">odelab_solver</span><span class="p">,</span> <span class="n">e</span><span class="p">)</span>
            <span class="c">#print msg</span>
            <span class="c">#print &#39;returning solution self.u as None&#39;</span>
            <span class="c">#return None, self.t</span>
            <span class="k">raise</span> <span class="ne">ValueError</span><span class="p">(</span><span class="n">msg</span><span class="p">)</span>

        <span class="c"># Retrive solution</span>
        <span class="n">t</span> <span class="o">=</span> <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">get_times</span><span class="p">()</span>
        <span class="k">if</span> <span class="nb">len</span><span class="p">(</span><span class="n">t</span><span class="p">)</span> <span class="o">!=</span> <span class="nb">len</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">t</span><span class="p">):</span>
            <span class="c"># Adaptive solver, need new t and u arrays</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">t</span> <span class="o">=</span> <span class="n">t</span>
            <span class="bp">self</span><span class="o">.</span><span class="n">_allocate_u</span><span class="p">(</span><span class="n">t</span><span class="p">)</span>
        <span class="k">with</span> <span class="bp">self</span><span class="o">.</span><span class="n">solver</span><span class="o">.</span><span class="n">open_store</span><span class="p">()</span> <span class="k">as</span> <span class="n">events</span><span class="p">:</span>
            <span class="k">if</span> <span class="bp">self</span><span class="o">.</span><span class="n">neq</span> <span class="o">==</span> <span class="mi">1</span><span class="p">:</span>
                <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[:]</span> <span class="o">=</span> <span class="n">events</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span>
            <span class="k">else</span><span class="p">:</span>
                <span class="k">for</span> <span class="n">i</span> <span class="ow">in</span> <span class="nb">range</span><span class="p">(</span><span class="bp">self</span><span class="o">.</span><span class="n">neq</span><span class="p">):</span>
                    <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">[:,</span> <span class="n">i</span><span class="p">]</span> <span class="o">=</span> <span class="n">events</span><span class="p">[</span><span class="n">i</span><span class="p">]</span>
        <span class="k">return</span> <span class="bp">self</span><span class="o">.</span><span class="n">u</span><span class="p">,</span> <span class="bp">self</span><span class="o">.</span><span class="n">t</span>


<span class="c">#------------------------------------------------------------------------------</span>
</div></div>
<div class="viewcode-block" id="list_all_solvers"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.list_all_solvers">[docs]</a><span class="k">def</span> <span class="nf">list_all_solvers</span><span class="p">():</span>
    <span class="sd">&quot;&quot;&quot;Return all solver classes in this package, excluding superclasses.&quot;&quot;&quot;</span>
    <span class="c"># Important: odespy.__init__.py must import all solver classes</span>
    <span class="c"># into the namespace for this function to work properly.</span>

    <span class="n">exclude</span> <span class="o">=</span> <span class="p">(</span><span class="s">&#39;Solver&#39;</span><span class="p">,</span><span class="s">&#39;Adaptive&#39;</span><span class="p">,</span> <span class="s">&#39;PyDS&#39;</span><span class="p">,</span> <span class="s">&#39;ode_scipy&#39;</span><span class="p">,</span> <span class="s">&#39;Odepack&#39;</span><span class="p">,</span>
               <span class="s">&#39;RungeKutta1level&#39;</span><span class="p">,</span> <span class="s">&#39;RungeKutta2level&#39;</span><span class="p">,</span> <span class="s">&#39;SolverImplicit&#39;</span><span class="p">,</span>
               <span class="s">&#39;MyRungeKutta&#39;</span><span class="p">,</span> <span class="s">&#39;MySolver&#39;</span><span class="p">)</span>
    <span class="kn">import</span> <span class="nn">odespy</span>
    <span class="n">classes</span> <span class="o">=</span> <span class="n">inspect</span><span class="o">.</span><span class="n">getmembers</span><span class="p">(</span><span class="n">odespy</span><span class="p">,</span> <span class="n">inspect</span><span class="o">.</span><span class="n">isclass</span><span class="p">)</span>
    <span class="n">solvers</span> <span class="o">=</span> <span class="p">[</span><span class="n">solver</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="k">for</span> <span class="n">solver</span> <span class="ow">in</span> <span class="n">classes</span>
               <span class="k">if</span> <span class="n">solver</span><span class="p">[</span><span class="mi">0</span><span class="p">]</span> <span class="ow">not</span> <span class="ow">in</span> <span class="n">exclude</span><span class="p">]</span>
    <span class="k">return</span> <span class="n">solvers</span>
</div>
<div class="viewcode-block" id="list_available_solvers"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.list_available_solvers">[docs]</a><span class="k">def</span> <span class="nf">list_available_solvers</span><span class="p">():</span>
    <span class="sd">&quot;&quot;&quot;Return all available solver classes in this package.&quot;&quot;&quot;</span>
    <span class="n">available_solvers</span> <span class="o">=</span> <span class="p">[]</span>
    <span class="kn">import</span> <span class="nn">odespy</span>
    <span class="n">all_solvers</span> <span class="o">=</span> <span class="n">list_all_solvers</span><span class="p">()</span>
    <span class="k">for</span> <span class="n">solvername</span> <span class="ow">in</span> <span class="n">all_solvers</span><span class="p">:</span>
        <span class="k">try</span><span class="p">:</span>      <span class="c"># Try to initialize solvers with f is None</span>
            <span class="n">method</span> <span class="o">=</span> <span class="nb">eval</span><span class="p">(</span><span class="s">&#39;odespy.</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="n">solvername</span><span class="p">)(</span><span class="bp">None</span><span class="p">)</span>
            <span class="n">available_solvers</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">solvername</span><span class="p">)</span>
        <span class="k">except</span><span class="p">:</span>
            <span class="k">try</span><span class="p">:</span>
                <span class="c"># Try the exception of linearly solvers in ODEPACK</span>
                <span class="c"># f is illegal for these solvers.</span>
                <span class="n">method</span> <span class="o">=</span> <span class="nb">eval</span><span class="p">(</span><span class="s">&#39;odespy.</span><span class="si">%s</span><span class="s">&#39;</span> <span class="o">%</span> <span class="n">solvername</span><span class="p">)()</span>
                <span class="n">available_solvers</span><span class="o">.</span><span class="n">append</span><span class="p">(</span><span class="n">solvername</span><span class="p">)</span>
            <span class="k">except</span><span class="p">:</span>
                <span class="c"># Failed to initialize this solver.</span>
                <span class="c"># Perhaps the required dependency is not installed.</span>
                <span class="k">pass</span>
    <span class="k">return</span> <span class="n">available_solvers</span>
</div>
<div class="viewcode-block" id="list_not_suitable_complex_solvers"><a class="viewcode-back" href="../../solvers.html#odespy.solvers.list_not_suitable_complex_solvers">[docs]</a><span class="k">def</span> <span class="nf">list_not_suitable_complex_solvers</span><span class="p">():</span>
    <span class="sd">&quot;&quot;&quot;List all solvers that do not work for complex-valued ODEs.&quot;&quot;&quot;</span>
    <span class="k">return</span> <span class="p">[</span>
        <span class="s">&#39;BogackiShampine&#39;</span><span class="p">,</span> <span class="s">&#39;CashKarp&#39;</span><span class="p">,</span> <span class="s">&#39;Dop853&#39;</span><span class="p">,</span> <span class="s">&#39;Dopri5&#39;</span><span class="p">,</span>
        <span class="s">&#39;DormandPrince&#39;</span><span class="p">,</span> <span class="s">&#39;Fehlberg&#39;</span><span class="p">,</span>
        <span class="s">&#39;RungeKutta1&#39;</span><span class="p">,</span>
        <span class="s">&#39;RungeKutta2&#39;</span><span class="p">,</span> <span class="s">&#39;RungeKutta3&#39;</span><span class="p">,</span> <span class="s">&#39;RungeKutta4&#39;</span><span class="p">,</span>
        <span class="s">&#39;Lsoda&#39;</span><span class="p">,</span> <span class="s">&#39;Lsodar&#39;</span><span class="p">,</span> <span class="s">&#39;Lsode&#39;</span><span class="p">,</span> <span class="s">&#39;Lsodes&#39;</span><span class="p">,</span>
        <span class="s">&#39;Lsodi&#39;</span><span class="p">,</span> <span class="s">&#39;Lsodis&#39;</span><span class="p">,</span> <span class="s">&#39;Lsoibt&#39;</span><span class="p">,</span>
        <span class="s">&#39;RKC&#39;</span><span class="p">,</span> <span class="s">&#39;RKF45&#39;</span><span class="p">,</span>
        <span class="s">&#39;odefun_sympy&#39;</span><span class="p">,</span> <span class="s">&#39;lsoda_scipy&#39;</span><span class="p">,</span>
        <span class="s">&#39;Radau5&#39;</span><span class="p">,</span> <span class="s">&#39;Radau5Explicit&#39;</span><span class="p">,</span> <span class="s">&#39;Radau5Implicit&#39;</span><span class="p">,</span>
        <span class="p">]</span>
</pre></div></div>

          </div>
        </div>
      </div>
      <div class="sphinxsidebar">
        <div class="sphinxsidebarwrapper">
<div id="searchbox" style="display: none">
  <h3>Quick search</h3>
    <form class="search" action="../../search.html" method="get">
      <input type="text" name="q" />
      <input type="submit" value="Go" />
      <input type="hidden" name="check_keywords" value="yes" />
      <input type="hidden" name="area" value="default" />
    </form>
    <p class="searchtip" style="font-size: 90%">
    Enter search terms or a module, class or function name.
    </p>
</div>
<script type="text/javascript">$('#searchbox').show(0);</script>
        </div>
      </div>
      <div class="clearer"></div>
    </div>
    <div class="related">
      <h3>Navigation</h3>
      <ul>
        <li class="right" style="margin-right: 10px">
          <a href="../../genindex.html" title="General Index"
             >index</a></li>
        <li class="right" >
          <a href="../../py-modindex.html" title="Python Module Index"
             >modules</a> |</li>
        <li class="right" >
          <a href="../../np-modindex.html" title="Python Module Index"
             >modules</a> |</li>
        <li><a href="../../index.html">Odespy API 0.2 documentation</a> &raquo;</li>
          <li><a href="../index.html" >Module code</a> &raquo;</li> 
      </ul>
    </div>
    <div class="footer">
        &copy; Copyright 2012, Liwei Wang and Hans Petter Langtangen.
      Created using <a href="http://sphinx.pocoo.org/">Sphinx</a> 1.1.2.
    </div>
  </body>
</html>